{"notes":[{"id":"classic-cnns/stn","category":"classic-cnns","legacyPath":"","legacySlug":"","legacyPaths":[],"title":"STN","subtitle":"乾坤大挪移","author":"Z. Yuan","paperDate":"2015-06-05","publishedOn":"2025-11-27","world":"external/stn","paperTitle":"Spatial Transformer Networks","paperUrl":"https://arxiv.org/abs/1506.02025","bibliography":{"title":"Spatial Transformer Networks","authors":["Max Jaderberg","Karen Simonyan","Andrew Zisserman","Koray Kavukcuoglu"],"url":"https://arxiv.org/abs/1506.02025","pdfUrl":"https://arxiv.org/pdf/1506.02025v3","codeUrl":null,"preprint":{"id":"1506.02025","submittedOn":"2015-06-05","url":"https://arxiv.org/abs/1506.02025"},"publication":null,"citation":"@misc{classiccnnsstn2015,\n  title = {{Spatial Transformer Networks}},\n  author = {Max Jaderberg and Karen Simonyan and Andrew Zisserman and Koray Kavukcuoglu},\n  year = {2015},\n  eprint = {1506.02025},\n  archivePrefix = {arXiv},\n  url = {https://arxiv.org/abs/1506.02025}\n}\n","citationPath":"/content/papers/citations/classic-cnns/stn.e823b15c17eb.bib"},"thumbnail":{"src":"/content/papers/assets/7b29191fd34e282fbd2d0fa901014f5770192cf1641d814b39b43a903817fb7f.png","width":480,"height":364},"locale":"zh-hant","path":"/content/papers/zh-hant/classic-cnns/stn.f52b008207b3.md","headings":[{"id":"定義問題","text":"定義問題","depth":2},{"id":"解決問題","text":"解決問題","depth":2},{"id":"三個零件","text":"三個零件","depth":3},{"id":"網格產生器從輸出往回找","text":"網格產生器：從輸出往回找","depth":3},{"id":"取樣器在格點之間取值","text":"取樣器：在格點之間取值","depth":3},{"id":"放進網路裡","text":"放進網路裡","depth":3},{"id":"討論","text":"討論","depth":2},{"id":"變形的-mnist","text":"變形的 MNIST","depth":3},{"id":"街景門牌號碼","text":"街景門牌號碼","depth":3},{"id":"鳥類細分類","text":"鳥類細分類","depth":3},{"id":"結論","text":"結論","depth":2}],"anchorAliases":{},"guide":null,"relatedReading":[{"id":"text-recognition/rare","relation":"referenced","topic":""}]},{"id":"text-recognition/rare","category":"text-recognition","legacyPath":"text-recognition/1603-rare","legacySlug":"1603-rare","legacyPaths":[],"title":"RARE","subtitle":"全自動校正","author":"Z. Yuan","paperDate":"2016","publishedOn":"2024-10-08","paperTitle":"Robust Scene Text Recognition With Automatic Rectification","paperUrl":"https://openaccess.thecvf.com/content_cvpr_2016/html/Shi_Robust_Scene_Text_CVPR_2016_paper.html","bibliography":{"title":"Robust Scene Text Recognition With Automatic Rectification","authors":["Baoguang Shi","Xinggang Wang","Pengyuan Lyu","Cong Yao","Xiang Bai"],"url":"https://openaccess.thecvf.com/content_cvpr_2016/html/Shi_Robust_Scene_Text_CVPR_2016_paper.html","pdfUrl":"https://openaccess.thecvf.com/content_cvpr_2016/papers/Shi_Robust_Scene_Text_CVPR_2016_paper.pdf","codeUrl":null,"preprint":null,"publication":{"venue":"CVPR","year":2016,"kind":"conference","url":"https://openaccess.thecvf.com/content_cvpr_2016/html/Shi_Robust_Scene_Text_CVPR_2016_paper.html"},"citation":"@inproceedings{textrecognitionrare2016,\n  title = {{Robust Scene Text Recognition With Automatic Rectification}},\n  author = {Baoguang Shi and Xinggang Wang and Pengyuan Lyu and Cong Yao and Xiang Bai},\n  year = {2016},\n  booktitle = {CVPR},\n  url = {https://openaccess.thecvf.com/content_cvpr_2016/html/Shi_Robust_Scene_Text_CVPR_2016_paper.html}\n}\n","citationPath":"/content/papers/citations/text-recognition/rare.e993d8c6fce6.bib"},"thumbnail":{"src":"/content/papers/assets/ede56fcdf7e421a6d8418d322e7a516326d84123169b83be8f9badb72fbb994e.jpg","width":1224,"height":496},"locale":"zh-hant","path":"/content/papers/zh-hant/text-recognition/rare.3c50b83aa0c1.md","headings":[{"id":"定義問題","text":"定義問題","depth":2},{"id":"解決問題","text":"解決問題","depth":2},{"id":"空間轉換網路","text":"空間轉換網路","depth":3},{"id":"定位網路","text":"定位網路","depth":3},{"id":"網格生成器","text":"網格生成器","depth":3},{"id":"取樣器","text":"取樣器","depth":3},{"id":"編碼器-解碼器","text":"編碼器-解碼器","depth":3},{"id":"字典輔助辨識","text":"字典輔助辨識","depth":3},{"id":"模型訓練","text":"模型訓練","depth":3},{"id":"評估指標","text":"評估指標","depth":3},{"id":"討論","text":"討論","depth":2},{"id":"與其他方法比較","text":"與其他方法比較","depth":3},{"id":"結論","text":"結論","depth":2}],"anchorAliases":{},"guide":null,"relatedReading":[{"id":"text-recognition/sar","relation":"comparison","topic":"彎曲與不規則文字的辨識"},{"id":"text-recognition/dan","relation":"comparison","topic":"彎曲與不規則文字的辨識"}]}],"text":"拿一張歪掉的手寫數字給卷積網路看，它通常還是認得出來。\n\n這份容忍度從哪裡來？一部分來自最大池化：在 $2\\times2$ 的小範圍裡取最大值，特徵稍微移動一兩格，輸出不會變。疊很多層之後，網路對位置的變化就有了一定的寬容。\n\n但這份寬容是一點一點累積出來的，範圍也固定。Google DeepMind 的 Max Jaderberg、Karen Simonyan、Andrew Zisserman 與 Koray Kavukcuoglu 在 2015 年 6 月放出這篇論文，後來發表在 NIPS 2015。他們想讓網路自己決定：這張圖應該怎麼移、怎麼縮放、怎麼轉，才最好認。\n\n## 定義問題\n\n作者先指出最大池化的限制。它的範圍通常很小，例如 $2\\times2$ 個像素，所以對位置的不變性要靠很多層的卷積與池化慢慢累積；中間層的特徵圖，對輸入的大幅變換其實沒有不變性。\n\n問題的根源是池化機制是事先寫死的：在哪裡取、取多大，跟輸入長什麼樣無關。\n\n作者想要一個不一樣的模組：\n\n- **看輸入決定怎麼變換**：每張圖各自得到一個變換，不是所有圖共用同一種處理。\n- **作用在整張特徵圖上**：可以裁切、縮放、旋轉，甚至做非剛性的變形，不受局部範圍限制。\n- **不需要額外標註**：沒有人告訴它正確的旋轉角度或框，它只從最後的任務損失學。\n- **可以直接用反向傳播訓練**：不用改最佳化流程，可以插進現有的卷積網路裡。\n\n先看結果長什麼樣：\n\n[![三列 MNIST 範例，每列四欄。(a) 是被平移、縮放、旋轉或加了雜訊的手寫數字；(b) 是模組預測的取樣框，以彩色四邊形畫在原圖上；(c) 是依取樣框變換後、被擺正放大的數字；(d) 是後面分類網路的預測，分別是 7、5、6](/content/papers/assets/7b29191fd34e282fbd2d0fa901014f5770192cf1641d814b39b43a903817fb7f.png)](/content/papers/assets/7b29191fd34e282fbd2d0fa901014f5770192cf1641d814b39b43a903817fb7f.png)\n\n*原論文 Figure 1，取自 [**v3 PDF 第 2 頁**](https://arxiv.org/pdf/1506.02025v3#page=2)。(a) 變形過的 MNIST 輸入；(b) 模組預測的變換；(c) 變換後的結果；(d) 後面分類網路的預測。整個網路只用類別標籤訓練。*\n\n第三列尤其清楚：數字 6 很小，旁邊還有雜點；模組自己框出 6 的位置，裁下來放大，交給後面的分類網路。從頭到尾，沒有人告訴它 6 在哪裡。\n\n## 解決問題\n\n### 三個零件\n\n[![空間變換模組的架構。輸入特徵圖 U 分成兩路：一路進入定位網路，輸出變換參數 θ，再由網格產生器算出取樣網格 T_θ(G)；另一路直接送進取樣器，取樣器依網格從 U 取樣，輸出特徵圖 V](/content/papers/assets/96a7134077ab04428f529111ff95e65d6863c038ad037e4d679cb1d2de57c0bb.png)](/content/papers/assets/96a7134077ab04428f529111ff95e65d6863c038ad037e4d679cb1d2de57c0bb.png)\n\n*原論文 Figure 2，取自 [**v3 PDF 第 3 頁**](https://arxiv.org/pdf/1506.02025v3#page=3)。定位網路、網格產生器與取樣器合起來，就是一個空間變換器。*\n\n整個模組由三個零件依序組成：\n\n1. **定位網路**（localisation net）：讀入特徵圖 $U$，輸出變換參數 $\\theta$。它可以是全連接網路，也可以是卷積網路，只要最後一層是迴歸層，輸出 $\\theta$ 就好。\n2. **網格產生器**（grid generator）：用 $\\theta$ 算出一組取樣點 $\\mathcal{T}_\\theta(G)$，也就是「輸出的每個像素，要到輸入的哪裡去取值」。\n3. **取樣器**（sampler）：照著取樣點，從 $U$ 取值，得到輸出 $V$。\n\n多通道的輸入，每個通道都用同一組變換，通道之間的空間對應才不會亂掉。\n\n定位網路沒什麼特別，重點在後面兩步。我們用一個小例子走一遍。\n\n### 網格產生器：從輸出往回找\n\n先假設變換是二維的仿射變換，只要 6 個參數：\n\n$$\n\\begin{pmatrix} x_i^s \\\\ y_i^s \\end{pmatrix}\n= \\mathcal{T}_\\theta(G_i)\n= \\begin{bmatrix} \\theta_{11} & \\theta_{12} & \\theta_{13} \\\\ \\theta_{21} & \\theta_{22} & \\theta_{23} \\end{bmatrix}\n\\begin{pmatrix} x_i^t \\\\ y_i^t \\\\ 1 \\end{pmatrix}\n$$\n\n$(x_i^t, y_i^t)$ 是輸出網格上第 $i$ 個像素的座標，上標 $t$ 是 target；$(x_i^s, y_i^s)$ 是它要去輸入取值的位置，上標 $s$ 是 source。\n\n方向值得留意：公式是從**輸出**的座標算出**輸入**的座標。這樣輸出的每個像素都一定有一個來源，不會有空洞，和電腦繪圖中的貼圖做法相同。\n\n座標都正規化到 $[-1, 1]$：輸出和輸入的左上角都是 $(-1, -1)$，右下角是 $(1, 1)$，所以同一組 $\\theta$ 不管特徵圖多大都適用。\n\n假設輸出是 $3\\times3$，我們想放大兩倍、看輸入的左上角，可以設 $\\theta_{11}=\\theta_{22}=0.5$、$\\theta_{13}=\\theta_{23}=-0.5$：\n\n```python\nimport torch\nimport torch.nn.functional as F\n\n# 輸出是 3×3 的規則網格；座標正規化到 [-1, 1]\ntheta = torch.tensor([[[0.5, 0.0, -0.5],\n                       [0.0, 0.5, -0.5]]])          # 放大 2 倍、看左上角\ngrid = F.affine_grid(theta, size=(1, 1, 3, 3), align_corners=True)\nprint(\"x_s：\\n\", grid[0, ..., 0])\nprint(\"y_s：\\n\", grid[0, ..., 1])\n```\n\n```text\nx_s：\n tensor([[-1.0000, -0.5000,  0.0000],\n        [-1.0000, -0.5000,  0.0000],\n        [-1.0000, -0.5000,  0.0000]])\ny_s：\n tensor([[-1.0000, -1.0000, -1.0000],\n        [-0.5000, -0.5000, -0.5000],\n        [ 0.0000,  0.0000,  0.0000]])\n```\n\n輸出網格的 $x^t$ 是 $-1, 0, 1$，乘以 0.5 再減 0.5，得到 $x^s = -1, -0.5, 0$：輸出的 3 個像素，只從輸入左半邊取值。$y$ 方向也一樣。輸出的 $3\\times3$，對應到輸入左上角的四分之一。\n\n[![兩組示意圖。(a) 輸入 U 上的綠色取樣點排成整齊的規則網格，和輸出 V 一一對應，輸出和輸入一樣；(b) 取樣點被仿射變換成一個傾斜縮小的平行四邊形，只蓋住數字的一部分，輸出 V 是被拉正、放大的數字](/content/papers/assets/89651828c63ac51ce8bd1efa4deffe57d50cca84735217ef8b2c9087b5b760c8.png)](/content/papers/assets/89651828c63ac51ce8bd1efa4deffe57d50cca84735217ef8b2c9087b5b760c8.png)\n\n*原論文 Figure 3，取自 [**v3 PDF 第 4 頁**](https://arxiv.org/pdf/1506.02025v3#page=4)。(a) 恆等變換：取樣網格就是規則網格；(b) 仿射變換後的取樣網格。*\n\n這張圖把同一件事畫出來。(a) 的取樣點排成規則的網格，輸出和輸入一樣；(b) 的取樣點被仿射變換成一個傾斜的平行四邊形，只蓋住輸入的一部分，輸出就是被裁切、旋轉、放大後的結果。\n\n仿射變換的 6 個參數可以表達裁切、平移、旋轉、縮放與斜切。左邊 $2\\times2$ 子矩陣的行列式絕對值小於 1 時，取樣網格會縮成一個面積更小的平行四邊形，等於裁切出一塊。\n\n$\\mathcal{T}_\\theta$ 也可以換成別的形式。作者舉了幾個例子：只允許裁切、平移與等比縮放的注意力形式（3 個參數 $s, t_x, t_y$）；8 個參數的平面投影變換；以及薄板樣條（thin plate spline，TPS），可以做非剛性的變形。唯一的條件是 $\\mathcal{T}_\\theta$ 對參數可微，梯度才能從取樣點傳回 $\\theta$。\n\n### 取樣器：在格點之間取值\n\n取樣點很少剛好落在整數格點上，所以取樣器需要一個插值核。作者寫成通用的形式，再以雙線性插值為主：\n\n$$\nV_i^c = \\sum_{n}^{H}\\sum_{m}^{W} U_{nm}^c\\,\\max\\!\\big(0,\\ 1-|x_i^s-m|\\big)\\,\\max\\!\\big(0,\\ 1-|y_i^s-n|\\big)\n$$\n\n每個輸出值，是離取樣點最近的四個像素加權平均，權重由距離決定。\n\n關鍵在於這個式子對 $U$ 和對取樣座標 $x_i^s$、$y_i^s$ 都可以求（次）梯度。梯度傳到取樣座標，就能再傳回 $\\theta$，最後傳到定位網路。\n\n我們換一組不會剛好落在格點上的 $\\theta$，用一張 $5\\times5$ 的輸入試試，像素值從左上的 0 到右下的 24：\n\n```python\nimport torch\nimport torch.nn.functional as F\n\nU = torch.arange(25, dtype=torch.float32).reshape(1, 1, 5, 5)   # 5×5 的輸入，值是 0 到 24\ntheta = torch.tensor([[[0.4, 0.0, -0.3],\n                       [0.0, 0.4, -0.3]]], requires_grad=True)\ngrid = F.affine_grid(theta, size=(1, 1, 3, 3), align_corners=True)\nprint(\"取樣的 x 座標（換成像素）：\", [round(v, 2) for v in ((grid[0, 0, :, 0] + 1) * 2).tolist()])\n\nV = F.grid_sample(U, grid, mode=\"bilinear\", align_corners=True)\nprint(V[0, 0])\n\nV.sum().backward()               # 隨便定一個損失，看梯度能不能回到 θ\nprint(theta.grad)\n```\n\n```text\n取樣的 x 座標（換成像素）： [0.6, 1.4, 2.2]\ntensor([[ 3.6000,  4.4000,  5.2000],\n        [ 7.6000,  8.4000,  9.2000],\n        [11.6000, 12.4000, 13.2000]], grad_fn=<SelectBackward0>)\ntensor([[[ 0.,  0., 18.],\n         [ 0.,  0., 90.]]])\n```\n\n這張輸入的值是「列 × 5 + 欄」。第一個取樣點落在第 0.6 列、第 0.6 欄，雙線性插值得到 $0.6\\times5+0.6=3.6$；它不在任何一個整數格點上，值是周圍四個像素依距離混合出來的。\n\n梯度也傳回了 $\\theta$。平移參數 $\\theta_{13}$ 的梯度是 18：取樣網格往右移一個正規化單位，等於移兩個像素，每個取樣值增加 2，9 個取樣點加起來就是 18。$\\theta_{23}$ 往下移，每格增加 10，加起來是 90。其他四個參數的梯度都是 0：這張輸入左右、上下都是均勻遞增的，網格以中心為準縮放或傾斜時，一側的取樣值變小、另一側變大，剛好抵消。\n\n這就是整個模組能端到端訓練的原因：損失對輸出 $V$ 的梯度，經過取樣器到達取樣座標，再經過網格產生器到達 $\\theta$，最後進入定位網路的權重。不需要任何人提供正確的變換。\n\n\n> [!NOTE]\n> \n> 雙線性插值在剛好落在格點上時不可微，只能用次梯度。作者也提到，實作上不需要真的對所有輸入位置求和，只要看每個取樣點周圍的四個像素，所以在 GPU 上可以算得很快。\n\n\n### 放進網路裡\n\n這個模組可以插在卷積網路的任何位置、插任意多個：\n\n- **串接在不同深度**：深層的模組看到的是更抽象的特徵，定位網路也有更多資訊可以判斷該怎麼變換。\n- **並排**：特徵圖中有好幾個物體或部位要分別處理時，可以並排幾個模組，各自聚焦一處。作者也提到限制：在純前饋網路裡，並排的模組數量就是網路能分別處理的物體數量上限。\n\n輸出的大小 $H'$、$W'$ 也可以和輸入不同，所以模組能順便降採樣。不過，雙線性這種支撐範圍很小的插值核，降採樣時可能產生混疊。\n\n## 討論\n\n### 變形的 MNIST\n\n作者把 MNIST 做成幾種變形版本：旋轉（R）；旋轉、平移、縮放（RTS）；投影變換（P）；彈性變形（E）。他們比較普通的全連接網路（FCN）、卷積網路（CNN），以及在輸入端加上空間變換模組的版本（ST-FCN、ST-CNN），變換分別用仿射（Aff）、投影（Proj）與 16 個控制點的 TPS。所有模型的參數量差不多，分類部分都是三個權重層，CNN 有兩層最大池化。\n\n| 模型 | R | RTS | P | E |\n| --- | ---: | ---: | ---: | ---: |\n| FCN | 2.1 | 5.2 | 3.1 | 3.2 |\n| CNN | 1.2 | 0.8 | 1.5 | 1.4 |\n| ST-FCN，Aff | 1.2 | 0.8 | 1.5 | 2.7 |\n| ST-FCN，TPS | 1.1 | 0.8 | 1.4 | 2.4 |\n| ST-CNN，Aff | 0.7 | 0.5 | 0.8 | 1.2 |\n| ST-CNN，Proj | 0.8 | 0.6 | 0.8 | 1.3 |\n| ST-CNN，TPS | 0.7 | 0.5 | 0.8 | 1.1 |\n\n*表：錯誤率（%）摘自原論文 Table 1，省略 ST-FCN 的投影變換版本。*\n\n每種變形下，加了模組的網路都比對應的基準好。最有意思的是 RTS 這一欄：ST-FCN 沒有任何卷積或池化，錯誤率 0.8%，和有兩層池化的 CNN 一樣。作者認為，這表示空間變換器是另一種得到空間不變性的方式。ST-CNN 又比 ST-FCN 更好，因為池化提供了更多不變性，卷積也更擅長處理局部結構。\n\n在 $60\\times60$、數字被平移、背景有雜點的版本上，差距更大：FCN 13.2%、CNN 3.5%、ST-FCN 2.0%、ST-CNN 1.7%。\n\n三種變換中，TPS 最強：它能把彈性變形的數字重新捏回接近標準的樣子，在簡單的旋轉資料上也沒有過擬合。作者還觀察到，所有模型都會把數字轉成直立的「標準」姿勢，也就是訓練資料中的平均姿勢。\n\n### 街景門牌號碼\n\nSVHN 是約 20 萬張真實的門牌照片，每張有 1 到 5 個數字，大小和排列變化很大，任務是辨識整串數字。作者的基準模型有 11 個隱藏層，最後接 5 個獨立的 softmax，各自預測一個位置的數字。\n\n在這個基準上，他們做了兩種擴充：\n\n- **ST-CNN Single**：在輸入之後加一個模組，定位網路是四層的卷積網路。\n- **ST-CNN Multi**：在前四層卷積前各加一個模組，定位網路都是兩層、每層 32 個單元的全連接網路；除了第一個，其餘模組變換的都是特徵圖。\n\n所有模組都用仿射變換與雙線性取樣，定位網路的迴歸層一律初始化成輸出恆等變換。\n\n| 模型 | 64px | 128px |\n| --- | ---: | ---: |\n| Maxout CNN | 4.0 | — |\n| CNN（作者的基準） | 4.0 | 5.6 |\n| DRAM* | 3.9 | 4.5 |\n| ST-CNN Single | 3.7 | 3.9 |\n| ST-CNN Multi | 3.6 | 3.9 |\n\n*表：序列錯誤率（%）摘自原論文 Table 2。64px 是以數字串為中心裁出的 $64\\times64$ 影像，128px 是裁得較鬆、背景較多的 $128\\times128$ 影像。DRAM 用了模型平均與蒙地卡羅平均，其他都是單一模型、單次前向。*\n\n64px 上，ST-CNN Multi 以 3.6% 創下當時最好成績。在背景更多的 128px 上，基準 CNN 退步到 5.6%，ST-CNN 仍維持 3.9%：模組把數字所在的區域裁下來放大，網路的解析度和容量都用在數字上。代價不大，ST-CNN Multi 的前向加反向只比基準 CNN 慢 6%。\n\n### 鳥類細分類\n\nCUB-200-2011 有 200 種鳥，約 6 千張訓練影像、5.8 千張測試影像；鳥的大小和方向不一，影像也沒有緊緊裁在鳥身上，要分辨種類，得看細部的紋理和形狀。\n\n作者的基準已經很強：一個 ImageNet 預訓練、加了 batch normalization 的 Inception 網路，在 CUB 上微調後達到 82.3%，超過先前最好的 81.0%。他們再並排 2 個或 4 個模組，用注意力形式的變換作用在輸入影像上；每個模組裁下的區塊交給各自的 Inception 子網路描述，最後串起來分類。整個網路只用類別標籤訓練。\n\n| 模型 | 準確率 |\n| --- | ---: |\n| CNN（基準），224px | 82.3% |\n| 2×ST-CNN，224px | 83.1% |\n| 2×ST-CNN，448px | 83.9% |\n| 4×ST-CNN，448px | 84.1% |\n\n*表：摘自原論文 Table 3。*\n\n4 個模組的版本達到 84.1%，比基準多 1.8 個百分點。作者也發現 ImageNet 的訓練集和 CUB 的測試集有 22 張重疊（共 5,794 張），移除這些影像後是 84.0%。\n\n更有趣的是模組學到的分工：2 個模組的版本中，一個學成了鳥頭偵測器，另一個盯著鳥的身體。過去的方法要用關鍵點標註，另外訓練每個部位的偵測器；這裡沒有任何部位標註，模組自己從資料中找出了部位。\n\n輸入可以用 448px 而不增加計算量，因為模組變換後的輸出會降採樣到 224px，再交給後面的網路處理。\n\n## 結論\n\n空間變換器把「怎麼看這張圖」也交給網路學：定位網路預測變換，網格產生器算出取樣位置，可微分的雙線性取樣讓梯度一路傳回去。整個模組不需要額外的標註，也不需要改動損失函數。\n\n實驗涵蓋了變形的 MNIST、真實的門牌照片和鳥類細分類，成績都比同條件的基準好；模組還在沒有任何提示的情況下，學會把數字擺正、把門牌數字裁出來、把鳥頭與鳥身分開看。作者也指出了它的邊界：並排的模組數量限制了能分別處理的物體數，降採樣時可能有混疊。\n\n空間變換器可以直接插進現有網路，不用改損失函數，也不用額外標註。PyTorch 已經內建 `affine_grid` 和 `grid_sample`，前面的範例就是用這兩個函式寫的，自己接一個並不難。\n\n如果你的資料裡有很多歪斜或透視變形，像街景裡的招牌文字，可以先在網路前面放一個試試看；[RARE](/blog/papers/text-recognition/rare) 就是這樣做文字辨識的。\n","imageSizes":{"/content/papers/assets/7b29191fd34e282fbd2d0fa901014f5770192cf1641d814b39b43a903817fb7f.png":{"width":480,"height":364},"/content/papers/assets/96a7134077ab04428f529111ff95e65d6863c038ad037e4d679cb1d2de57c0bb.png":{"width":832,"height":330},"/content/papers/assets/89651828c63ac51ce8bd1efa4deffe57d50cca84735217ef8b2c9087b5b760c8.png":{"width":820,"height":364}}}
