本页目录

Winograd算法

Winograd算法是Shmuel Winograd在1980年提出的用来减少FIR滤波器计算量的一个算法(这里的grad和梯度没有关系),但当时并没有引起太多关注。直到后来人们发现此算法可以用来加速CNN网络的卷积运算,才得到广泛应用。

Winograd

一维

考虑一个一维卷积,输入信号,卷积核,输出为,则有:

但是可以观察到,计算中存在重复,例如。这些计算一共用到了6次乘法和4次加法。现在做如下变换,记

则有:

因为卷积核事先已知,含的式子可以提前算好,因此只需计算~(各1次乘法、1次加法)和(各2次加法),总共4次乘法和8次加法。

乘法通常比加法耗时更长,因此减少乘法次数可以提高计算效率。

矩阵形式表示

Winograd已经证明了对于卷积核长度为的一维卷积,计算个输出所需的最少乘法数量为 。将上面的计算过程写成矩阵形式为:

其中的是哈达玛积(Hadamard Product),代表逐元素乘积。

是卷积核变换矩阵,尺寸为,对应到上例有:

是输入变换矩阵,尺寸为,对应到上例有:

是输出变换矩阵,尺寸为,对应到上例有:

二维

推广到二维情形,假设输入是图像,卷积核大小,则首先通过Img2col展开成矩阵乘法,再分块使用Winograd。

img

对于划分的每一小块,都可以使用一维Winograd算法计算;而整体来看,如果把每个分块都当作一个元素,则同理可以再用一次一维Winograd算法计算。

从计算的效率来说,先分析整体,对分块矩阵进行Winograd算法,这时会需要4矩阵乘;而每次矩阵乘再用Winograd算法,需要4次数乘,整个过程共需要16次乘法。如果使用常规的卷积操作则需要36次乘法。

算法的特点

Winograd算法通过减少乘法次数来实现提速,但是加法的数量会相应增加,也需要额外的变换计算及存储变换矩阵。随着卷积核和分块尺寸增大,需要考虑加法、变换和存储的代价,而且分块越大,变换矩阵越大,提效收益降低。

因此,Winograd适用于较小的卷积核和分块。

参考资料

本文的部分内容、图片来源于: