Logo
Section 1 / 7

卷积的原理

了解卷积操作及其在深度学习中的应用。

导入

卷积的原理

了解卷积操作及其在深度学习中的应用。

为什么使用卷积?

我们之前见到的全连接层并不尊重输入数据的空间结构。例如,当输入是一张图像时,神经网络会将二维结构破坏,展平为一维向量。为了解决这个问题,人们设计了卷积神经网络(CNN)。这类网络在计算机视觉任务中表现极为出色。

在处理图像时为何要使用卷积?因为我们事先知道,相邻像素通常具有相似的特征,因此我们希望在网络设计中显式地利用这一先验知识。这种假设被称为归纳偏置(inductive bias)。

卷积层充分利用了数据的局部结构特性。

Representation of a Convolutional Neural Network
Representation of a Convolutional Neural Network
卷积神经网络示意图

但如何才能专注于局部结构,而不是像全连接层那样对整个输入做线性组合呢?

答案非常简单:我们将卷积层的操作限制在一个称为“卷积核”(kernel)的局部窗口上,然后在整个输入图像上滑动这个窗口。

卷积操作

卷积神经网络的基本运算就是卷积。数学上,两个二维函数之间的卷积定义如下:

(f∗g)(i,j)=∑a∑bf(a,b)g(i−a,j−b)(f*g)(i,j) = \sum_{a} \sum_{b} f(a,b)g(i-a,j-b)

尽管在数学中,其中一个信号在滑动前需要翻转,但在深度学习中通常忽略这一点。原因在于卷积核内部的权重是可训练的,网络会自动学习合适的参数。

Convolution between two signals
Convolution between two signals
两个信号之间的卷积过程

直观来看,我们可以将一个 2×2 的卷积核作用于一个 4×4 的图像,如下图所示:

The convolution operation
The convolution operation
卷积操作示意图

尝试想象卷积核在图像上滑动的过程。注意,每次卷积核与图像区域之间的运算实际上是点积运算,结果是一个标量(在输出中以蓝色显示)。

该输出被称为特征图(feature map)。

可以看出,给定一个矩阵(输入)和一个较小的权重矩阵(卷积核),我们可以生成一个标量值。这个数值本质上是输入局部区域与卷积核之间点积的结果。

值得注意的是,这种点积实际上衡量了两者的相关性(或相似度)。卷积神经网络擅长学习邻近像素之间的空间相关性。

下面是一个图像中 3×3 区域(称为图像块,patch)与一个 3×3 卷积核进行卷积的例子:

f∗g=[abcdefghi]∗[123456789]f*g = \begin{bmatrix}a & b & c \\ d & e & f \\g & h & i \end{bmatrix} * \begin{bmatrix} 1 & 2 & 3 \\4 & 5 & 6 \\7 & 8 & 9 \end{bmatrix}

f∗g=(a⋅1)+(b⋅2)+(c⋅3)+(d⋅4)+(e⋅5)+(f⋅6)+(g⋅7)+(h⋅8)+(i⋅9)f*g = (a\cdot1) +(b\cdot2) +(c\cdot3) + (d\cdot4) + (e\cdot5) + (f\cdot6)+ (g\cdot7) + (h\cdot8) + (i\cdot9)

再次强调,这只是一个简单的点积运算。

总结一下: 给定一个 N×NN \times N 的输入矩阵和一个 p×pp \times p 的卷积核(其中 p<Np < N):

  • 我们将卷积核在输入矩阵的所有可能位置上滑动;
  • 在每个位置执行一次点积运算,得到一个标量;
  • 将所有这些标量汇总起来,形成输出,即特征图。

那么我们实现了什么目标?

我们将输入空间中的一个二维矩阵转换到了特征空间,同时保留了其二维结构。这样,网络能够捕捉仅出现在图像局部区域的上下文信息,而这些信息若使用全连接层则会被丢失。

直观上,卷积神经网络能够识别图像中的模式,如边缘、角点、圆形等。从另一个角度看,卷积神经网络可以被视为一种局部连接的神经网络——与全连接网络不同,特征图中的每一个像素只受输入图像的一个局部区域影响,而非整幅图像。

重要说明

  • 卷积仍是一种线性运算。
  • 卷积核中的权重是可训练的,并且在整个输入上共享。
  • 每次点积运算都反映了输入局部区域与卷积核之间的相似程度。
  • 卷积操作可以在任意维度上进行。
  • 滑动的方向决定了卷积的维度:对于图像,是二维卷积;但对于具有一维局部结构的序列数据,也可以应用一维卷积。

如果你理解了卷积的基本原理,就应该能够用 Python 从零实现卷积操作。这只需要几行代码。在下面的练习中,你将编写一个函数,接收一个二维图像和一个二维卷积核,输出它们的卷积结果。

你的代码将在四张不同的图像上进行测试。卷积核大小始终为 (3, 3),而图像尺寸分别为 (8, 8)、(12, 10)、(10, 10) 和 (12, 8)。

1import torch 2 3def conv2d(image, kernel): 4 pass

训练神经网络

实际应用中的卷积