全卷积神经网络FCN详解(附带Tensorflow详解代码实现) (2)

 我们甚至可以把这个2*2的feature map,每一个像素点隔开一个空格,空格里的数字填充为0,周围的padding填充的数字也全都为零,然后再继续上采样,得到一个5*5的特征图,如下所示:

全卷积神经网络FCN详解(附带Tensorflow详解代码实现)

 

 这样咱们的反卷积就完成了。那么什么是1*1卷积呢?

四.1*1卷积

在我们的卷积神经网络前向传播的过程当中,最后是一个N*N*21的输出,这个21是可以我们进行人为通过1*1卷积定义出来的,这样我们才能够得到一个21个类别,每个类别出现的概率,最后输出和原图图像大小一致的那个特征图,每个像素点上都有21个channel,表示这个像素点所具有的某个类别输出的概率值。吴恩达教授在讲解卷积神经网络的时候,用到了一张十分经典的图像来表示1*1卷积:

全卷积神经网络FCN详解(附带Tensorflow详解代码实现)

 

 原本的特征图长宽为28,channel为192,我们可以通过这种卷积,使用32个卷积核将28*28*192变成一个28*28*32的特征图。在使用1*1卷积时,得到的输出长款保持不变,channel数量和卷积核的数量相同。可以用抽象的3d立体图来表示这个过程:

全卷积神经网络FCN详解(附带Tensorflow详解代码实现)

 

 因此我们可以通过控制卷积核的数量,将数据进行降维或者升维。增加或者减少channel,但是feature map的长和宽是不会改变的。我们在全卷积神经网络(FCN)正向传播,下采样的最后一步(可以查看本博客的第一张图片)就是将一个N*N*4096的特征图变成了一个N*N*21的特征图。

五.全卷积神经网络的跳级实现(skip)

我们如果直接采用首先卷积,然后上采样得到与原图尺寸相同特征图的方法的话,进行语义分割的效果经过实验是不太好的。因为在进行卷积的时候,在特征图还比较大的时候,我们提取到的图像信息非常丰富,越到后面图像的信息丢失得就越明显。我们可以发现经过最前面的五次卷积和池化之后,原图的分别率分别缩小了2,4,8,16,32倍。对于最后一层的的图像,需要进行32倍的上采样才能够得到和原图一样的大小,但仅依靠最后一层图像做上采样,得到的结果还是不太准确,一些细节依然很不准确。因此作者采用了跳级连接的方法,即将在卷积的前几层提取到的特征图分别和后面的上采样层相连,然后再相加继续网上往上上采样,上采样多次之后就可以得到和原图大小一致的特征图了,这样也可以在还原图像的时候能够得到更多原图所拥有的信息。如下图所示:

全卷积神经网络FCN详解(附带Tensorflow详解代码实现)

 

 

 作者最先提出的跳级连接是把第五层的输出进行上采样,然后和池化层4的预测相结合起来,最后得到原图的策略,这个策略叫做FCN-16S,之后又尝试了和所有池化层结合起来预测的方法叫做FCN-8S,发现这个方法准确率是最高的。如下图所示:

全卷积神经网络FCN详解(附带Tensorflow详解代码实现)

 

 Groud Truth表示原始图像的人为标注,前面的都是神经网络做出的预测。跳级连接,我们这类给出的原图的大小是500*500*3,这个尺寸无所谓,因为全卷积神经网络可接受任意尺寸大小的图片。我们首先从前面绿色刚刚从池化层做完maxpool的特征图上做一次卷积然后,然后再把下一个绿色的特征图做卷积,最后把16*16*21,已经做完1*1卷积的输出,把这个三个输出相加在一起,这样就实现了跳级(skip)输入的实现,再把这几个输入融合之后的结果进行上采样,得到一个568*568*21的图,将这个图通过一个softmax层变成500*500*21的特征图,因此图像的长宽和原图一模一样了,每一个像素点都有21个概率值,表示这个像素点属于某个类别的概率,除了和原图的channel不同之外没啥不同的。

然后我们来看基于Tensorflow的代码实现。

六.Tensorflow代码实现全卷积神经网络

首先导包并读取图片数据:

内容版权声明:除非注明,否则皆为本站原创文章。

转载注明出处:https://www.heiqu.com/zygpzs.html