【ICCV-2019】ACNet:通过非对称卷积块增强CNN的核骨架 3*3卷积==>1*3卷积+3*1卷积=白给的精度提升
論文:https://arxiv.org/pdf/1908.03930v1.pdf
代碼:https://github.com/ShawnDing1994/ACN
通過非對稱卷積塊增強CNN的核骨架
- 摘要
- 1.研究背景
- 2. 相關工作
- 2.1 非對稱卷積
- 2.2 CNN架構中的中性結構
- 3. 方法
- 3.1 公式
- 3.2 利用卷積的可加性
- 3.3 ACB不增加任何推理時間開銷
- 4. 實驗
- 4.1 在CIFAR上的性能改進
- 4.2 在ImageNet上的性能改進
- 4.3 消融研究
- 4.4 ACB增強方形核的骨架
- 5. 結論
- ACBlock
- Demo
下面要介紹的論文發于ICCV2019,題為「ACNet:Strengthening the Kernel Skeletons for Powerful CNN via Asymmetric ConvolutionBlocks」
摘要
由于在給定的應用環境中,設計合適的卷積神經網絡(CNN)結構,需要大量人工的工作或大量的GPU資源消耗,研究界正在尋找網絡結構無關的CNN結構,這種結構可以很容易地插入到多個成熟的體系結構中,以提高我們實際應用程序的性能。我們提出了非對稱卷積塊(ACB)作為CNN的構造塊,它使用一維非對稱卷積核來增強方形卷積核,我們用ACBs代替標準的方形卷積核來構造一個非對稱卷積網絡ACNet,該網絡可以訓練到更高的精度。訓練后,我們等價地將ACNet轉換為相同的原始架構,因此將不需要額外的計算。實驗證明,ACNet可以在CIFAR和ImageNet上顯著提高各種經典模型的性能。
1.研究背景
卷積神經網絡在視覺理解方面取得了巨大的成功,這使得其可以應用在安全系統、移動電話、汽車等各種應用中。由于前端設備通常受限于計算資源,就要求網絡在保證精度的條件下要盡可能輕量。另一方面,隨著CNN架構設計的相關研究增多,模型的性能得到了顯著改善,但當現有的模型不能滿足我們的特定需求時,要定制一種新的架構需要花費極高的成本。最近,研究者們正在尋求與架構無關的新型CNN結構,例如SE塊和準六邊形內核,它們可以直接和各種網絡結構結合使用,以提高它們的性能。最近對CNN結構的研究主要集中在以下兩個方面:
1)層之間是如何相互連接的,例如簡單的堆疊在一起、恒等映射、密集連接等;
2)如何組合不同層的輸出以提高學習表示的質量;
本文提出了非對稱卷積塊(ACB),它是用三個并行的d×d,1×d,d×1d\times d,1\times d,d\times 1d×d,1×d,d×1核來代替原始的 d×dd\times dd×d 核,如圖Figure1所示:
給定一個網絡,我們通過將每個方形卷積核替換為ACB模塊,并訓練網絡到收斂。之后我們將每個ACB中非對稱核的權值加到方形核的對應位置,將ACNet轉換為和原始網絡等效的結構。ACNet可以提高基準模型的性能,在CIFAR和ImageNet上優勢明顯。更好的是,ACNet引入了0參數,因此無需仔細調參就能將其與不同的CNN結構結合起來,并且易于在主流CNN框架上實現,以及不需要額外的推理時間開銷。
2. 相關工作
2.1 非對稱卷積
非對稱卷積通常用于逼近現有的正方形卷積以進行模型壓縮和加速,先前的一些工作表明,可以將標準的 d×dd \times dd×d 卷積分解為 1×d1 \times d1×d 和 d×1d \times 1d×1 卷積,以減少參數量。其背后的理論相當簡單:如果二維卷積核的秩為1,則運算可等價地轉換為一系列一維卷積。然而,由于深度網絡中下學習到的核具有分布特征值,其內在秩比實際中的高,因此直接將變換應用于核會導致顯著的信息損失。Denton等人基于SVD分解找到一個低秩逼近,然后對上層進行精細化以恢復性能。Jaderberg等人通過最小化重構誤差,成功學習了水平核和垂直核。Jin等人應用結構約束使二維卷積可分離,在獲得相當精度的條件下時間加速了2倍。另一方面,非對稱卷積也被廣泛的用來做網絡結構設計,例如Inception-v3中,7*7卷積被1*7卷積和7*1卷積代替。語義分割ENet網絡也采用這種方法來設計高效的語義分割網絡,雖然精度略有下降,但降低了33%的參數量。
2.2 CNN架構中的中性結構
我們不打算修改CNN架構,而是使用一些與架構無關的結構來增強現有的模型。因此,我們的方法對任何網絡都是有效的。例如,SE塊可以附加到卷積層后,使用學習到的權重重新縮放特征圖通道數,從而在合理的附加參數量和計算代價下顯著提高精度。作為另一個示例,可以將輔助分類器插入模型中以幫助監督學習過程,這確實可以提高性能,但是需要額外的人為調整超參數。相比之下,ACNet在訓練中不會引入任何超參數,并且在推理過程中不需要額外的參數和計算。因此,在實際應用中,開發人員可以使用ACNet來增強各種模型,而無需進行詳細的參數調整,并且最終用戶可以享受性能提升而又不會減慢推理速度。
3. 方法
3.1 公式
對于一個尺寸為 H×WH \times WH×W 通道數為D的卷積核,以通道數為C的特征圖作為輸入,我們使用 F∈RH×W×CF \in R^{H\times W\times C}F∈RH×W×C 表示卷積核, M∈RU×V×CM \in R^{U\times V\times C}M∈RU×V×C 表示輸入,這是一個尺寸為UxV通道數為C的特征圖, O∈RR×T×DO\in R^{R\times T\times D}O∈RR×T×D代表輸出特征圖。對于這個層的第j個卷積核,相應的輸出特征映射通道是:
其中*是二維卷積算子。M:,:,kM_{:,:,k}M:,:,k?是M的第k個通道的尺寸為UxV的特征圖,F:,:,k(i)F_{:,:,k}^{(i)}F:,:,k(i)? 代表 F(j)F^{(j)}F(j) 的第k個通道的尺寸為HxW的特征圖。在現代CNN體系結構中,批量歸一化(BN)被廣泛使用,以減少過度擬合,加快訓練過程。通常情況下,批量歸一化層之后通常會接一個線性變化,以增強表示能力。和公式1相比,輸入變成:
其中,μj\mu_jμj?和σj\sigma_jσj?是批標準化的通道平均值和標準差,γj\gamma_jγj?和βj\beta_jβj?是縮放系數和偏移量。
3.2 利用卷積的可加性
我們試圖以不對稱卷積可以等效地融合到標準方形核層中的方式來使用,這樣就不會引入額外的推理時間計算負擔。我們注意到卷積的一個有用性質:如果幾個大小兼容的二維核在相同的輸入上以相同的步幅操作以產生相同分辨率的輸出,并且它們的輸出被求和,我們可以將這些核在相應的位置相加,從而得到一個產生相同輸出的等效核。也就是說,二維卷積的可加性可以成立,即使核大小不同。
其中 III 是一個矩陣,K(1)K^{(1)}K(1) 和 K(2)K^{(2)}K(2) 是具有兼容尺寸的兩個2D核,
是在對應位置的求和操作。注意 III 可能會被裁剪或者執行Padding操作。這里,“兼容”意味著我們可以把較小的內核“修補”到較大的內核上。在形式下,p層和q的下面這種轉換是可行的:
例如,3x1和1x3是和3x3兼容的。通過研究滑動窗口形式的卷積計算,可以很容易地驗證這一點,如圖Figure2所示:
對于一個特定的卷積核F(j)F^{(j)}F(j),一個指定的點y,則輸出 O:,:,jO_{:,:,j}O:,:,j? 可以使用下式計算:
其中,X是輸入M上相應的滑動窗口。顯然,當我們將兩個濾波器產生的輸出通道相加時,如果一個通道上的每個y,其在另一個通道上的對應點共享相同的滑動窗口,則其相加性質(等式3)成立。
3.3 ACB不增加任何推理時間開銷
在本文中,我們關注3x3卷積,這在現代CNN體系結構中大量使用。在給定的體系結構下,我們通過簡單地將每個3x3卷積層替換為ACB來構建ACNet,該ACB模塊包含三個并行層,內核大小分別為3x3,1x3,和3x1。和標準CNN的常規做法類似,在三層中的每一層之后都進行批量歸一化,這被成為分子,并將三個分支的輸出綜合作為ACB的輸出。請注意,我們可以使用與原始模型相同的配置來訓練ACNet,而無需調整任何額外的超參數。如4.1和4.2節中所示,我們可以訓練ACNet達到更高的精度。訓練完成后,我們嘗試將每個ACB轉換為產生相同輸出的標準卷積層這樣,與經過常規訓練的對等方相比,我們可以獲得不需要任何額外計算的功能更強大的網絡。該轉換通過兩個步驟完成,即BN融合和分支融合。
BN融合 卷積的同質性使得后續的BN和線性變換可以等價的融合到具有附加偏置的卷積層中。從公式2可以看出,對于每個分支,如果我們構造一個新的內核 γjσjF(j){{\gamma_j}\over{\sigma_j}}F^{(j)}σj?γj??F(j)
然后加上偏置 ?μjγjσj+βj-{{\mu_j\gamma_j}\over{\sigma_j}}+\beta_j?σj?μj?γj??+βj? ,我們可以產生相同的輸出。
分支融合 我們通過在平方核的相應位置加入非對稱核,將三個BN融合分支合并成標準卷積層。在實際應用中,這種轉換是通過建立一個原始結構的網絡并使用融合的權值進行初始化來實現的,這樣我們就可以在與原始結構相同的計算預算下產生與ACNet相同的輸出。更正式地,對于第j個卷積核, F′(j)F^{'(j)}F′(j) 表示融合后的卷積核, bjb_jbj? 代表偏置, Fˉ(j)\bar F^{(j)}Fˉ(j) 和 F^(j)\hat F^{(j)}F^(j) 分別代表1x3和3x1卷積核的輸出,融合后的結果可以表示為:
然后我們可以很容易地驗證對于任意濾波器j,
其中, O:,:,j,Oˉ:,:,j,O^:,:,jO_{:,:,j},\bar O_{:,:,j},\hat O_{:,:,j}O:,:,j?,Oˉ:,:,j?,O^:,:,j? 代表原始 3×3,1×3,3×13\times 3,1\times 3,3\times 13×3,1×3,3×1 三個分支的輸出。Figure3展示了這個過程。
值得注意的是,盡管可以將ACB等價地轉換為標準層,但是等效值僅在推理時才成立,因為訓練動態是不同的,從而導致不同的性能。訓練過程的不等價性是由于內核權重的隨機初始化,以及由它們參與的不同計算流得出的梯度。
4. 實驗
我們進行了大量的實驗來驗證ACNet在一系列數據集和架構上提高CNN性能的有效性。具體地說,我們選擇一個現成的體系結構作為基線,構建一個ACNet的對等物,從頭開始培訓它,將它轉換為與基線相同的結構,并測試它以收集準確性。對于可比性,所有的模型都經過訓練直到完全收斂,并且每一對基線和ACNet使用相同的配置,例如,學習速率計劃和批大小。
4.1節和4.2節,論文在CIFAR10和CIFAR100數據集,ImageNet數據集進行對比測試,結果如Table1,Table2,Table3所示。
4.3 節還展示了消融研究,也就是對AlexNet和ResNet在ImageNet圖像上進行測試,采用控制變量法控制ACB的三個關鍵影響因素,同時對比了將圖片旋轉的測試效果,最終使用了ACB模塊全部技巧的網絡模型獲得了幾乎所有測試情況的新SOTA結果,證明了ACB模塊能夠增加對數據旋轉的適應能力。
4.4 節用以說明ACB增強了方形卷積核的骨架信息。論文在訓練過程中通過隨機丟棄網絡中3*3卷積核的骨架權重和邊角權重,所謂骨架權重和邊角權重的定義如Figure 4所示,骨架權重就是和中間位置直接相連的4個位置加上自身,剩下的就是邊角部分了。
4.1 在CIFAR上的性能改進
為了對我們的方法在各種CNN架構上進行初步的評價,我們在CIFAR-10和CIFAR-100上對幾個有代表性的基準模型Cifar-quick、VGG16、ResNet-56、WRN-16-8和DenseNet-40進行了實驗。
對于Cifar-quick、VGG-16、ResNet-56和DenseNet-40,我們按照慣例使用0.1、0.01、0.001和0.0001的階梯學習率訓練模型。對于WRN-16-8,我們遵循原始論文[35]中報告的訓練配置。我們使用了所采用的數據增強技術,即填充到40 40,隨機裁剪和左右翻轉。
從表1和表2中可以看出,所有模型的性能都有明顯的提升,這表明ACBs的好處可以與各種架構相結合。
4.2 在ImageNet上的性能改進
然后,通過在ImageNet上的一系列實驗,我們繼續在真實世界的應用程序上驗證我們的方法的有效性,這些實驗包括來自1000個類的128萬張用于訓練的圖像和50K用于驗證的圖像。我們分別用AlexNet、ResNet-18和DenseNet-121作為plain-style、residual和dense - connected架構的代表。每個模型以256個批處理規模進行150個epoch的訓練,這比通常采用的基準(如90 epoch)要長,因此精度的提高不能簡單歸結為基礎模型的不完全收斂。對于數據的增強,我們采用標準的管道,包括包圍框扭曲,左右翻轉和顏色移動,作為一個常見的實踐。特別是我們使用的AlexNet的普通版本來自Tensorflow GitHub,它由五個堆疊的卷積層和三個完全連接的層組成,沒有本地響應歸一化(LRN),也沒有跨gpu連接。值得注意的是,由于AlexNet的前兩層分別使用了11 × 11和5 × 5核,因此可以擴展ACBs使其具有更大的非對稱核。但是對于這兩層我們仍然只使用1× 3和3 × 1的卷積,因為這樣大規模的卷積在現代CNN中越來越不受歡迎,使得大型的ACBs不那么有用。
如表3所示,單作物Top-1精度AlexNet、ResNet-18和DenseNet-121提升1.52%,分別為0.78%和1.18%。在實踐中,針對相同的精度目標,我們可以使用ACNet來增強一個更高效的模型,以更少的推理時間、能量消耗和存儲空間來實現目標。另一方面,在計算預算或模型大小相同的限制下,我們可以使用ACNet以明顯的優勢提高精度,從而從終端用戶的角度來看,所獲得的性能可以被視為免費的利益。
4.3 消融研究
雖然我們有經驗證明ACNet的有效性,但我們仍然希望找到一些解釋。在本節中,我們試圖通過一系列消融研究來研究ACNet。具體來說,我們關注以下三個設計決策:1)水平核,2)垂直核,3)每個分支中的批處理規范化。為了具有可比性,我們使用相同的訓練配置,在ImageNet上用不同的消融來訓練幾個AlexNet和ResNet-18模型。值得注意的是,如果去掉分支中的批歸一化,我們將對整個ACB的輸出進行批歸一化,即批歸一化層的位置由預求和變為后求和。
從表4可以看出,去掉這三種設計中的任何一種都會降低模型的質量。然而,盡管水平和垂直的卷積都可以提高性能,由于在實踐中水平方向和垂直方向的處理不平等,可能會存在一些差異,例如:我們通常執行隨機的左右翻轉,而不是上下翻轉圖像來增強訓練數據。因此,如果在模型中輸入一幅倒置的圖像,原始的3 × 3層應該產生無意義的結果,這是自然的,但是水平核將在軸對稱位置產生與原始圖像相同的輸出(圖4),部分ACB仍能提取出正確的特征。考慮到這一點,我們假設ACBs可以增強模型對旋轉畸變的魯棒性,使模型能夠更好地泛化未見數據。
然后,我們用整個驗證集的旋轉扭曲圖像測試之前訓練的模型,包括逆時針90?旋轉,180?旋轉,和上下翻轉。當然,每個模型的精度都顯著降低,但水平核模型在180度旋轉和上下翻轉圖像上提供了明顯更高的精度。例如,ResNet-18在水平方向上的精度略低于在垂直方向上的精度,但在180度方向上的精度要高0.75%。與基礎模型相比,其在原/ 180度翻轉圖像上的精度分別提高了0.34% / 1.27%。可以預見,模型發揮類似的性能在180度旋轉和上下翻轉輸入,因為180度旋轉+左右翻轉等價于上下翻轉,由于數據增強方法,模型對左右翻轉具有魯棒性。
總之,我們已經證明,acb,特別是內部的水平核,可以增強模型的魯棒性,以可觀的邊際旋轉畸變。雖然這可能不是ACNet有效的主要原因,但我們認為它有希望激發對轉動不變性問題的進一步研究。
4.4 ACB增強方形核的骨架
直觀地看,當向平方內核添加水平和垂直內核時,可以將其視為顯式增強骨架部分的方法,我們試圖通過研究骨骼和角落重量之間的差異來解釋ACNet的有效性。
受CNN剪枝的啟發,我們首先在不同的空間位置刪除一些權值,然后在CIFAR-10上使用ResNet56觀察性能下降。具體地,我們在核中隨機設置一些單獨的權值為零,并對模型進行檢驗。如圖5a所示,標注為轉角的曲線,我們從每個角的四個角中隨機選擇權重
為獲得給定的每個卷積層的全局稀疏度比,將它們設為0。注意,4/9 = 44.4%,44%的稀疏比意味著去掉四個角的大部分權值。對于骨架,我們只從每個核的骨架中隨機選擇權值。對于全局,內核中的每個權重都有平等的被選擇的機會。實驗采用不同的隨機種子重復5次,并繪制了mean±std曲線。
然后,畫出不同丟棄比例下的測試集準確率圖,如Figure5所示:
通過對比圖Figure5(a)和Figure5(b)發現,丟棄骨架部分的權重會降低準確率,而丟棄邊角部分的權重卻能獲得更好的精度。然后,我們通過研究卷積核的數值來研究上敘述現象發生的原因。我們使用幅度(即絕對值)作為衡量參數重要性的指標,許多先前的CNN加速工作都采用了該指標。具體來說,我們將一個卷積層中所有融合的2D卷積核都加起來,通過最大值進行逐層歸一化,最后獲得所有層的歸一化核的平均值。更正式地,我們讓 F(i,j)F^{(i,j)}F(i,j) 表示第i個3x3卷積層的第j個核,L代表3x3卷積層的個數,max和abs代表逐像素的求最大值和取絕對值操作,所以平均核矩陣可以計算為:
其中,
我們在Figure 4(a)和Figure 4(b)上給出了經過正常訓練的ResNet56和融合了ACNet的A值。某個網格的數值和顏色表示該參數在所有位置上平均重要性。從Figure5(a)看出正常訓練的ResNet56參數分布是不平衡的,即中心點的A值最大,而四個角點的A值最小。Figure5(b)顯示ACNet加劇了這種不平衡,因為四個角點的A值減小到了0.4以下,并且骨架中心點的A值為1.0,這意味著該位置在每個3*3層中始終占據主導地位。值得注意的是,方向,水平,垂直核的相應位置上的權重可能會在符號上相反,因此它們將它們相加可能會產生更大或者更小的幅度。但我們觀察到一個一致的現象,即模型學會了在每一層增強骨骼部位的權重。我們繼續研究如果將非對稱核加到其他位置而不是中心骨架時模型的行為。具體來說,我們使用和以前相同的訓練配置來訓練Resnet56的ACNet對應網絡,但是將水平卷積核向下平移一個像素,垂直卷積核向右平移一個像素。因此,在分支融合時,我們得到Figure 4?的結果。我們觀察到, 這樣的ACB網絡還可以增強邊界,但是強度不如常規ACB對骨骼的增強。該模型的準確度為94.67%,比常規的ACNet低0.42%(Table1)。此外我們對模型融合進行了類似的消融實驗,可以看到丟棄邊角部分的參數仍然獲得了最高的精度,丟棄增強的右下角邊界不會比丟棄左上角2*2方形的權重得到更好的結果。
總結一下
1)3*3卷積核的骨架部分比邊角部分更加重要;
2)ACB可以增強卷積核的骨架部分,從而提高性能;
3)和常規的ACB相比,將水平和垂直核添加到邊界會降低模型的性能;
4)這樣做也可以增加邊界的重要性,但是不能削弱其它部分的重要性。
因此,我們將ACNet的有效性部分歸因于它進一步增強卷積核骨架的能力。
5. 結論
為了提高各種CNN架構的性能,我們提出了非對稱卷積塊(ACB),該算法將三個分別具有正方形,水平和垂直核的卷積分支的輸出求和。我們通過使用ACB替換成熟體系結構中的方形核卷積層來構建非對稱卷積網絡(ACNet),并在訓練后將其轉換為原始網絡結構。在CIFAR和ImageNet數據集上,通過在經典網絡上使用ACNet評估我們的性能,取得了SOTA結果。我們已經表明,ACNet可以以可觀察的幅度增強模型對旋轉失真的魯棒性,并顯著增強方形卷積核的骨骼部分。并且ACNet也易于使用主流框架實現,方便研究者follow這項工作。
ACBlock
import torch.nn as nn import torch.nn.init as init from custom_layers.crop_layer import CropLayerclass ACBlock(nn.Module):def __init__(self, in_channels, out_channels, kernel_size, stride=1, padding=0, dilation=1, groups=1,padding_mode='zeros', deploy=False,use_affine=True, reduce_gamma=False, use_last_bn=False, gamma_init=None):super(ACBlock, self).__init__()self.deploy = deployif deploy:self.fused_conv = nn.Conv2d(in_channels=in_channels, out_channels=out_channels,kernel_size=(kernel_size, kernel_size), stride=stride,padding=padding, dilation=dilation, groups=groups, bias=True,padding_mode=padding_mode)else:self.square_conv = nn.Conv2d(in_channels=in_channels, out_channels=out_channels,kernel_size=(kernel_size, kernel_size), stride=stride,padding=padding, dilation=dilation, groups=groups, bias=False,padding_mode=padding_mode)self.square_bn = nn.BatchNorm2d(num_features=out_channels, affine=use_affine)center_offset_from_origin_border = padding - kernel_size // 2ver_pad_or_crop = (padding, center_offset_from_origin_border)hor_pad_or_crop = (center_offset_from_origin_border, padding)if center_offset_from_origin_border >= 0:self.ver_conv_crop_layer = nn.Identity()ver_conv_padding = ver_pad_or_cropself.hor_conv_crop_layer = nn.Identity()hor_conv_padding = hor_pad_or_cropelse:self.ver_conv_crop_layer = CropLayer(crop_set=ver_pad_or_crop)ver_conv_padding = (0, 0)self.hor_conv_crop_layer = CropLayer(crop_set=hor_pad_or_crop)hor_conv_padding = (0, 0)self.ver_conv = nn.Conv2d(in_channels=in_channels, out_channels=out_channels, kernel_size=(kernel_size, 1),stride=stride,padding=ver_conv_padding, dilation=dilation, groups=groups, bias=False,padding_mode=padding_mode)self.hor_conv = nn.Conv2d(in_channels=in_channels, out_channels=out_channels, kernel_size=(1, kernel_size),stride=stride,padding=hor_conv_padding, dilation=dilation, groups=groups, bias=False,padding_mode=padding_mode)self.ver_bn = nn.BatchNorm2d(num_features=out_channels, affine=use_affine)self.hor_bn = nn.BatchNorm2d(num_features=out_channels, affine=use_affine)if reduce_gamma:assert not use_last_bnself.init_gamma(1.0 / 3)if use_last_bn:assert not reduce_gammaself.last_bn = nn.BatchNorm2d(num_features=out_channels, affine=True)if gamma_init is not None:assert not reduce_gammaself.init_gamma(gamma_init)def init_gamma(self, gamma_value):init.constant_(self.square_bn.weight, gamma_value)init.constant_(self.ver_bn.weight, gamma_value)init.constant_(self.hor_bn.weight, gamma_value)def single_init(self):init.constant_(self.square_bn.weight, 1.0)init.constant_(self.ver_bn.weight, 0.0)init.constant_(self.hor_bn.weight, 0.0)def forward(self, input):if self.deploy:return self.fused_conv(input)else:square_outputs = self.square_conv(input)square_outputs = self.square_bn(square_outputs)vertical_outputs = self.ver_conv_crop_layer(input)vertical_outputs = self.ver_conv(vertical_outputs)vertical_outputs = self.ver_bn(vertical_outputs)horizontal_outputs = self.hor_conv_crop_layer(input)horizontal_outputs = self.hor_conv(horizontal_outputs)horizontal_outputs = self.hor_bn(horizontal_outputs)result = square_outputs + vertical_outputs + horizontal_outputsif hasattr(self, 'last_bn'):return self.last_bn(result)return resultclass CropLayer(nn.Module):# E.g., (-1, 0) means this layer should crop the first and last rows of the feature map. And (0, -1) crops the first and last columnsdef __init__(self, crop_set):super(CropLayer, self).__init__()self.rows_to_crop = - crop_set[0]self.cols_to_crop = - crop_set[1]assert self.rows_to_crop >= 0assert self.cols_to_crop >= 0def forward(self, input):if self.rows_to_crop == 0 and self.cols_to_crop == 0:return inputelif self.rows_to_crop > 0 and self.cols_to_crop == 0:return input[:, :, self.rows_to_crop:-self.rows_to_crop, :]elif self.rows_to_crop == 0 and self.cols_to_crop > 0:return input[:, :, :, self.cols_to_crop:-self.cols_to_crop]else:return input[:, :, self.rows_to_crop:-self.rows_to_crop, self.cols_to_crop:-self.cols_to_crop]Demo
這個Demo非常簡單,在一張256*256的灰度圖像上,分別做卷積核為(3,3)的運算,以及先進行卷積核為(1,3)的運算、然后進行卷積核為(3,1)的運算,比較二者的差異。
- 項目結構
- 主要代碼
- 實驗結果
總結
以上是生活随笔為你收集整理的【ICCV-2019】ACNet:通过非对称卷积块增强CNN的核骨架 3*3卷积==>1*3卷积+3*1卷积=白给的精度提升的全部內容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: IT日常技能:VMware网络配置
- 下一篇: 【腾讯面试题】SQL语句优化方法有哪些?