经典机器学习方法(7)—— 卷积神经网络CNN

2024-06-22 16:36

本文主要是介绍经典机器学习方法(7)—— 卷积神经网络CNN,希望对大家解决编程问题提供一定的参考价值,需要的开发者们随着小编来一起学习吧!

  • 参考:《动手学深度学习》第六章

  • 卷积神经网络(convolutional neural network,CNN)是一类针对图像数据设计的神经网络,它充分利用了图像数据的特点,具有适合图像特征提取的归纳偏置,因而在图像相关任务上,它可以用相比全连接网络更少的参数量取得更好的性能。基于 CNN 的模型已经在 CV 领域处于主导地位,当今几乎所有的图像识别、目标检测或语义分割相关的学术竞赛和商业应用都以这种方法为基础
  • 即使在通常使用循环神经网络的一维序列结构任务上(例如音频、文本和时间序列分析),卷积神经网络也越来越受欢迎。 通过对卷积神经网络一些巧妙的调整,它们也能在图结构数据和推荐系统中发挥作用
  • 本文介绍卷积神经网络的基础结构,不涉及任何先进模型和新架构

文章目录

  • 1. 从全连接层到卷积层
    • 1.1 不变性
    • 1.2 MLP 的局限性
    • 1.3 卷积
      • 1.3.1 卷积的数学定义
      • 1.3.2 互相关运算
    • 1.4 通道
  • 2. 图像卷积
    • 2.1 卷积核的特征提取能力
    • 2.2 学习卷积核
    • 2.3 特征映射和感受野
  • 3. 填充和步幅
    • 3.1 填充
    • 3.2 步幅
  • 4. 多输入多输出通道
    • 4.1 多输入通道
    • 4.2 多输出通道
    • 4.3 只作用在通道上的 1X1 卷积层
  • 5. 汇聚层
    • 5.1 最大汇聚层与平均汇聚层
    • 5.2 填充和步幅
    • 5.3 多个通道
  • 6. 卷积神经网络

1. 从全连接层到卷积层

  • 前文 经典机器学习方法(3)—— 多层感知机 我们训练 MLP 解决了图像分类问题。为了适配 MLP 的输入形式,我们直接把尺寸为 (1,28,28) 的原始图像数据拉平成 28x28 的一维数据,这种做法破坏了图像的空间结构信息,原本图像中相近像素之间具有相互关联性,这些性质并不能被 MLP 利用
  • MLP 适合处理表格数据,其中行对应样本,列对应特征,我们寻找的模式可能涉及特征之间的交互,但是我们不能预先假设任何与特征交互相关的先验结构,换句话说,MLP 不具有任何归纳偏置,其训练效率随数据维度上升而不断下降,最终导致模型不再实用

    考虑一个图像分类任务,每张图像具有百万级像素,这意味着 MLP 的每次输入都有 1 0 6 10^6 106 维度,一个将其降维到 1000 的全连接层将有 1 0 9 10^9 109 个参数,这几乎和 GPT1 的总参数量相当

1.1 不变性

  • 针对图像数据而言,一个设计良好的模型应当对图像的某些变换具有容忍性,这被称为模型的不变性
    1. 平移不变性:图像中的目标物体在发生平移后,模型仍然能有效识别。原始 CNN 可以通过局部连接权值共享这两个设计实现平移不变性
    2. 旋转不变性:图像中的目标物体在发生旋转后,模型仍然能有效识别。原始 CNN 不具备这种能力,需要通过数据增强(构造随机旋转的样本)和特定的网络结构(如旋转卷积和旋转不变池化)来实现
    3. 尺度不变性:图像中的目标物体在放大或缩小后,模型仍然能有效识别。原始 CNN 不具备这种能力,需要通过数据增强(构造随机缩放的样本)和特定的网络结构(如多尺度特征融合)来实现
  • 原始 CNN 仅具备平移不变性,它也常被称为空间不变性,为了实现这一点,模型应当具有以下归纳偏置
    1. 平移不变:不管检测对象出现在图像中的哪个位置,神经网络的前面几层应该对相同的图像区域具有相似的反应
    2. 局部原则:神经网络的前面几层应该只探索输入图像中的局部区域,而不过度在意图像中相隔较远区域的关系。最后通过聚合这些局部特征,在整个图像级别进行预测

1.2 MLP 的局限性

  • 设 MLP 的输入是二维图像 X ∈ R I × J \mathbf{X}\in\mathbb{R}^{I\times J} XRI×J,其隐藏表示为 H ∈ R I × J \mathbf{H}\in\mathbb{R}^{I\times J} HRI×J,用 [ X ] i , j {[\mathbf{X}]_{i, j} } [X]i,j [ H ] i , j {[\mathbf{H}]_{i, j} } [H]i,j 分别表示输入图像和隐藏表示中位置 ( i , j ) (i,j) (i,j) 处的像素

    注意,真实 MLP 中 X , H \mathbf{X,H} X,H 都应当是一维的,这里为了方便理解,认为无论输入还是隐藏表示都拥有二维空间结构

  • 设 MLP 的权重和偏置参数分别为 W , U \mathbf{W,U} W,U 全连接层可以表示为
    [ H ] i , j = [ U ] i , j + ∑ k ∑ l [ W ] i , j , k , l [ X ] k , l = [ U ] i , j + ∑ ∑ l [ V ] i , j , a , b [ X ] i + a , j + b (1) \begin{aligned} {[\mathbf{H}]_{i, j} } & =[\mathbf{U}]_{i, j}+\sum_{k} \sum_{l}[\mathbf{W}]_{i, j, k, l}[\mathbf{X}]_{k, l} \\ & =[\mathbf{U}]_{i, j}+\sum \sum^{l}[\mathbf{V}]_{i, j, a, b}[\mathbf{X}]_{i+a, j+b} \end{aligned} \tag{1} [H]i,j=[U]i,j+kl[W]i,j,k,l[X]k,l=[U]i,j+l[V]i,j,a,b[X]i+a,j+b(1) 其中从 W \mathbf{W} W V \mathbf{V} V 的转换只是形式上从绝对位置索引变成相对位置索引,即有 [ V ] i , j , a , b = [ W ] i , j , i + a , j + b [\mathbf{V}]_{i, j, a, b}=[\mathbf{W}]_{i, j, i+a, j+b} [V]i,j,a,b=[W]i,j,i+a,j+b,此处索引 a , b a,b a,b 通过正负偏移覆盖了整个图像。上式意味着:隐藏表示中任意给定位置 [ H ] i , j {[\mathbf{H}]_{i, j} } [H]i,j 处的隐藏值,可以通过在 X \mathbf{X} X 中以为 ( i , j ) (i,j) (i,j) 为中心对像素进行加权求和得到,加权使用的权重为 [ V ] i , j , a , b [\mathbf{V}]_{i, j, a, b} [V]i,j,a,b
  • 现在将 1.1 节的两个归纳偏置引入以上全连接层计算式中。
    1. 首先考虑平移不变性,这意味着检查对象在输入 X \mathbf{X} X 中的平移应导致隐藏表示 H \mathbf{H} H 中的平移,这意味着 V , U \mathbf{V,U} V,U 不能依赖于目标位置 ( i , j ) (i,j) (i,j),即 [ V ] i , j , a , b = [ V ] a , b [\mathbf{V}]_{i, j, a, b} = [\mathbf{V}]_{a, b} [V]i,j,a,b=[V]a,b,且 U \mathbf{U} U 是一个常数,这时 H \mathbf{H} H 的定义可以简化为
      [ H ] i , j = u + ∑ a ∑ b [ V ] a , b [ X ] i + a , j + b (2) [\mathbf{H}]_{i, j}=u+\sum_{a} \sum_{b}[\mathbf{V}]_{a, b}[\mathbf{X}]_{i+a, j+b} \tag{2} [H]i,j=u+ab[V]a,b[X]i+a,j+b(2) 机器学习领域中,以上运算被称为 卷积convolution,注意我们此时用系数 [ V ] a , b [\mathbf{V}]_{a, b} [V]a,b ( i , j ) (i,j) (i,j) 附近的像素 ( i + a , j + b ) (i+a,j+b) (i+a,j+b) 加权计算 [ H ] i , j [\mathbf{H}]_{i, j} [H]i,j由于 [ V ] a , b [\mathbf{V}]_{a, b} [V]a,b 不再依赖于目标位置,其参数量相比 [ V ] i , j , a , b [\mathbf{V}]_{i,j,a, b} [V]i,j,a,b 减少了很多,这就是利用归纳偏置提升模型效率的体现
    2. 进一步考虑局部性。局部原则说明我们不应用偏移 ( i , j ) (i,j) (i,j) 太远的信息计算隐藏值 [ H ] i , j [\mathbf{H}]_{i, j} [H]i,j,为此我们对偏移 a , b a,b a,b 的绝对值设置上限 △ \triangle H \mathbf{H} H 的定义进一步简化为
      [ H ] i , j = u + ∑ a = − Δ Δ ∑ b = − Δ Δ [ V ] a , b [ X ] i + a , j + b (3) [\mathbf{H}]_{i, j}=u+\sum_{a=-\Delta}^{\Delta} \sum_{b=-\Delta}^{\Delta}[\mathbf{V}]_{a, b}[\mathbf{X}]_{i+a, j+b} \tag{3} [H]i,j=u+a=ΔΔb=ΔΔ[V]a,b[X]i+a,j+b(3) 执行以上计算的神经网络层被称为 卷积层(convolutional layer),其中 V \mathbf{V} V 被称为 卷积核(convolution kernel)/滤波器(filter),亦或简单地称之为该卷积层的权重,通常该权重是可学习的参数
  • 我们通过引入归纳偏置将全连接层变成了卷积层,大幅降低了需要学习的权重 U , V \mathbf{U,V} U,V 的参数量,这并不是没有代价的。归纳偏置的引入其实限制了网络的表示能力,卷积层无法汇聚长跨度信息,也无法考虑目标的绝对位置信息
    • 当偏置与目标场景(图像数据)相符时,这种表示能力的限制是有益的,它相当于做了一个剪枝,避免了大量无用参数的训练,在不影响模型性能的情况下提升了训练效率
    • 当偏置与目标场景(图像数据)不符时,比如当图像不满足平移不变时,模型可能难以拟合我们的训练数据

1.3 卷积

1.3.1 卷积的数学定义

  • 进一步讨论之前,首先明确一下以上提到的卷积运算。首先,数学中卷积本质是一个泛函积分公式,它将两个函数 f , g : R d → R f,g:\mathbb{R}^d\to\mathbb{R} f,g:RdR 映射到一个数,定义为
    ( f ∗ g ) ( x ) = ∫ f ( z ) g ( x − z ) d z (4) (f*g)(\mathbf{x}) = \int f(\mathbf{z})g(\mathbf{x-z})d\mathbf{z} \tag{4} (fg)(x)=f(z)g(xz)dz(4) 也就是说,卷积是当把一个函数“翻转”并移位 x \mathbf{x} x 时( g ( z ) → g ( − z ) → g ( x − z ) g(\mathbf{z})\to g(-\mathbf{z})\to g(\mathbf{x}-\mathbf{z}) g(z)g(z)g(xz) ),测量 f , g f,g f,g 之间的重叠。当自变量为离散对象时,积分就变成求和。例如,对于由索引为整数 Z \mathbb{Z} Z 的、平方可和的、无限维向量集合中抽取的向量,我们得到以下定义
    ( f ∗ g ) ( i ) = ∑ a f ( a ) g ( i − a ) (5) (f*g)(i) = \sum_a f(a)g(i-a) \tag{5} (fg)(i)=af(a)g(ia)(5) 进一步推广到二维张量的情况
    ( f ∗ g ) ( i , j ) = ∑ a ∑ b f ( a , b ) g ( i − a , j − b ) . (6) (f * g)(i, j)=\sum_{a} \sum_{b} f(a, b) g(i-a, j-b) . \tag{6} (fg)(i,j)=abf(a,b)g(ia,jb).(6) 注意这个 (6) 式本质和 1.2 节的 (3) 式是一样的,我们总是可以匹配两者间的符号
  • 下面给出两个例子,帮助读者直观理解卷积的物理含义
    • 如果一个系统输入 f 是不稳定的,消耗 g 是稳定的,那么可以用卷积求这个系统的存量。下面是一个吃饭的例子,图中 f , g f,g f,g 分别表示一个人的进食曲线和食物的消化曲线。 f ( t ) f(t) f(t) 表示在t时刻吃下的食物量, g ( t ) g(t) g(t) 表示吃下事物后 t t t 时刻食物量的比例值。左上图给出了这个人在 8/10/12 点吃下三种东西的量,左下图显示了 14 点时三种食物的消化剩余比例,右侧表格列举了 14 点时三种食物的剩余量,将其求和就是卷积运算,我们可以用卷积求取任意时刻此人肚子里剩余的实物总量
      在这里插入图片描述
      下图可视化了卷积中的 “翻转-平移” 操作
      在这里插入图片描述
      这种不稳定输入和稳定消耗的场景在信号与系统中经常用出现,一个典型场景是系统处理输入的最高速率有限,而每时每刻输入系统的信号量是不定的,这时就可以用卷积计算系统积压的未处理信息量
    • 卷积可以理解为影响因素的叠加,此时 f 表示影响源的强度,g 表示影响随时间或距离的缩放系数。一个例子是噪音的叠加,此时可以把 f f f 看作一条直路上各个坐标位置噪音源的强度, g g g 表示噪音随距离增加的衰减系数,则路上任意一点处的真实噪声强度也可以通过卷积计算。图像卷积可以看作这个例子的二维推广

1.3.2 互相关运算

  • 了解了卷积的数学定义后,回头看式 (3) 给出的图像卷积运算
    [ H ] i , j = u + ∑ a = − Δ Δ ∑ b = − Δ Δ [ V ] a , b [ X ] i + a , j + b [\mathbf{H}]_{i, j}=u+\sum_{a=-\Delta}^{\Delta} \sum_{b=-\Delta}^{\Delta}[\mathbf{V}]_{a, b}[\mathbf{X}]_{i+a, j+b} [H]i,j=u+a=ΔΔb=ΔΔ[V]a,b[X]i+a,j+b 现在尝试把它对应到 1.3.1 节的数学定义,这时原始图像 X \mathbf{X} X 相当于影响强度 f f f,卷积核 V \mathbf{V} V 相当于影响系数 g g g,忽略偏置 u u u,上式可改写为
    [ H ] i , j = ∑ a = − Δ Δ ∑ b = − Δ Δ g ( a , b ) f ( i + a , j + b ) [\mathbf{H}]_{i, j}=\sum_{a=-\Delta}^{\Delta} \sum_{b=-\Delta}^{\Delta} g(a, b) f(i+a, j+b) \\ [H]i,j=a=ΔΔb=ΔΔg(a,b)f(i+a,j+b) 再令 a ′ = i + a , b ′ = j + b a'=i+a, b'=j+b a=i+a,b=j+b,把相对位置改写成绝对位置,有
    [ H ] i , j = ∑ a ′ ∑ b ′ g ( a ′ − i , b ′ − j ) f ( a ′ , b ′ ) (7) [\mathbf{H}]_{i, j}=\sum_{a'} \sum_{b'} g(a'-i, b'-j) f(a', b') \tag{7} [H]i,j=abg(ai,bj)f(a,b)(7)
  • 将 (7) 式和标准卷积运算 ( f ∗ g ) ( i , j ) = ∑ a ∑ b g ( i − a , j − b ) f ( a , b ) (f * g)(i, j)=\sum_{a} \sum_{b} g(i-a, j-b) f(a, b) (fg)(i,j)=abg(ia,jb)f(a,b) 对比,可见 CNN 中的卷积并不是标准卷积,只有把卷积核水平和垂直翻转后才是标准卷积,准确地讲,CNN 中这种运算称为 互相关(cross-correlation) 运算。尽管如此,由于卷积核参数是从数据中学习到的,因此无论这些层执行严格的卷积运算还是互相关运算,卷积层的输出都不会受到影响

    为了与深度学习文献中的标准术语保持一致,我们将继续把“互相关运算”称为卷积运算

1.4 通道

  • 以上讨论中,我们都把图像视为黑白的,即只有一个灰度通道,但是彩色图片都有 R/G/B 三个通道,某些特殊图像如光电图可能含有更多通道的信息,故大多数图像都是三维张量,其中前两个轴与像素的空间位置有关,第三轴可以看作每个像素的多维表示
  • 由于输入图像是三维的,我们的隐藏表示也最好采用三维张量。换句话说,对于每一个空间位置,我们想要采用一组而不是一个隐藏表示。因此,我们可以把隐藏表示想象为一系列具有二维张量的通道channel。 这些通道有时也被称为特征映射feature maps,因为每个通道都向后续层提供一组空间化的学习特征。 直观上可以想象在靠近输入的底层,一些通道专门识别边缘,而一些通道专门识别纹理
  • 为了支持输入 X \mathbf{X} X 和隐藏表示 H \mathbf{H} H 中的多个通道,我们将卷积公式调整如下
    [ H ] i , j , d = ∑ a = − Δ Δ ∑ b = − Δ Δ ∑ c [ V ] a , b , c , d [ X ] i + a , j + b , c [\mathrm{H}]_{i, j, d}=\sum_{a=-\Delta}^{\Delta} \sum_{b=-\Delta}^{\Delta} \sum_{c}[\mathbf{V}]_{a, b, c, d}[\mathbf{X}]_{i+a, j+b, c} [H]i,j,d=a=ΔΔb=ΔΔc[V]a,b,c,d[X]i+a,j+b,c

2. 图像卷积

  • 本节中,我们暂时忽略通道(第三维),看看卷积核是如何作用于二维图像数据,算出隐藏表示的。下面给出二维互相关运算的示意图,这里原始输入尺寸是 ( 3 , 3 ) (3,3) (3,3),卷积核尺寸 ( 2 , 2 ) (2,2) (2,2),滑动步长 ( 1 , 1 ) (1,1) (1,1)。(注意:将核函数上下左右翻转则是标准卷积运算)
    在这里插入图片描述
    卷积窗口从输入张量的左上角开始,从左到右、从上到下滑动。 当卷积窗口滑动到新一个位置时,包含在该窗口中的部分张量与卷积核张量进行按元素相乘,得到的张量再求和得到一个单一的标量值,由此我们得出了这一位置的输出张量值。输出的隐藏表示尺寸为输入尺寸 ( n h , n w ) (n_h,n_w) (nh,nw) 减去卷积核大小 ( k h , k w ) (k_h, k_w) (kh,kw)
    ( n h − k h + 1 ) × ( n w − k w + 1 ) (n_h-k_h+1) \times (n_w-k_w+1) (nhkh+1)×(nwkw+1) 稍后,我们将看到如何通过在图像边界周围填充零来保证有足够的空间移动卷积核,从而保持输出大小不变

2.1 卷积核的特征提取能力

  • 不同的卷积核可以对原始输入做出不同的处理,从而提取图像的各类特征。我们可以手工设计出提取水平特征和垂直特征的卷积核
    在这里插入图片描述
    类似地,还可以设计提取边缘特征和对图像进行一些处理的卷积核
    在这里插入图片描述

2.2 学习卷积核

  • 对于复杂的 CV 任务而言,手工设计的卷积核不一定是最合适的,注意到卷积核其实就是卷积层中的待学习权重,完全可以通过梯度下降方法通过数据驱动的形式自动学出来
  • 下面给出一个学习垂直边缘检查卷积核的简单示例,为简单起见,在此使用 pytorch 内置的二维卷积层并忽略偏置
    import torch
    from torch import nn# 构造一个二维卷积层,它具有1个输出通道和形状为(1,2)的卷积核
    conv2d = nn.Conv2d(1,1, kernel_size=(1, 2), bias=False)# 构造一个黑白图像
    X = torch.ones((6, 8))  # 初始化为全白
    X[:, 2:6] = 0           # 中间设置一块黑区域# 构造边缘检查结果
    Y = torch.zeros((6, 7))
    Y[:,1] = 1              # 1代表从白色到黑色的边缘
    Y[:,-2] = -1            # -1代表从黑色到白色的边缘# 这个二维卷积层使用四维输入和输出格式(批量大小、通道、高度、宽度),
    # 其中批量大小和通道数都为1
    X = X.reshape((1, 1, 6, 8))
    Y = Y.reshape((1, 1, 6, 7))
    lr = 3e-2  # 学习率for i in range(10):Y_hat = conv2d(X)l = (Y_hat - Y) ** 2conv2d.zero_grad()l.sum().backward()# 迭代卷积核conv2d.weight.data[:] -= lr * conv2d.weight.gradif (i + 1) % 2 == 0:print(f'epoch {i+1}, loss {l.sum():.3f}')
    
  • 训练结束后,观察学习到的卷积核
    conv2d.weight.data.reshape((1, 2))
    >>> tensor([[ 0.9910, -0.9936]])
    

2.3 特征映射和感受野

  • 如 1.4 节所述,某个通道的卷积层输出有时被称为 特征映射/特征图feature map,因为它可以被视为一个输入映射到下一层的空间维度的转换器。 在卷积神经网络中,对于某一层的任意元素 x x x,其 感受野receptive field 是指在前向传播期间可能影响计算的所有元素(来自所有先前层)
  • 注意,感受野可能大于输入的实际大小。还是以本节开头的图为例
    在这里插入图片描述
    给定 2 × 2 2\times 2 2×2 卷积核,阴影输出元素值19的感受野是输入阴影部分的四个元素。现在设上图的输入和输出分别为 X , Y \mathbf{X,Y} X,Y,现在我们在其后附加一个卷积层,该卷积层以 Y \mathbf{Y} Y 为输入,输出单个元素 z z z
    1. z z z Y \mathbf{Y} Y 上的感受野包括 Y \mathbf{Y} Y 的所有四个元素
    2. z z z X \mathbf{X} X 上的感受野包括 X \mathbf{X} X 的所有九个输入元素
  • 因此,当一个特征图中的任意元素需要检测更广区域的输入特征时,我们可以构建一个更深的网络

3. 填充和步幅

  • 从以上第2节的例子可知,卷积的输出形状 ( n h − k h + 1 ) × ( n w − k w + 1 ) (n_h-k_h+1) \times (n_w-k_w+1) (nhkh+1)×(nwkw+1) 取决于输入尺寸 ( n h , n w ) (n_h,n_w) (nh,nw) 和卷积核大小 ( k h , k w ) (k_h, k_w) (kh,kw),这种关系可能不够灵活,比如
    1. 有时在连续应用卷积之后,最终得到的输出远小于输入大小,原始图像许多的边界信息丢失了,填充padding 是解决此问题最有效的方法
    2. 有时原始的输入的分辨率可能过高了,我们希望大幅降低图像的宽度和高度,此时 步幅stride 可以提供帮助

3.1 填充

  • 卷积核尺寸大于 ( 1 , 1 ) (1,1) (1,1) 时,边界信息的丢失是不可避免的,虽然可能仅丢失了边缘的几个像素,但当多个卷积层堆叠时,累计丢失的像素就不可忽略的。填充padding 通过在输入图像边缘填充元素(通常填充0)来解决这个问题

    给出一个示例,原始输入尺寸为 ( 3 , 3 ) (3,3) (3,3),我们将其填充到 ( 5 , 5 ) (5,5) (5,5),使输出尺寸增加到 ( 4 , 4 ) (4,4) (4,4)
    在这里插入图片描述

  • 通常,如果我们添加 p h p_h ph 行填充和 p w p_w pw 列填充,则输出形状将为
    ( n h − k h + p h + 1 ) × ( n w − k w + p w + 1 ) (n_h-k_h+p_h+1) \times (n_w-k_w+p_w+1) (nhkh+ph+1)×(nwkw+pw+1) 这意味着输出的高度和宽度分别增加 p h p_h ph p w p_w pw许多时候我们设置 p h = k h − 1 p_h=k_h-1 ph=kh1 p w = k w − 1 p_w=k_w-1 pw=kw1,使输出和输入具有相同的尺寸,这样可以在构建网络时更容易地预测每个图层的输出形状
  • 卷积神经网络中卷积核的高度和宽度通常为奇数,好处是
    1. 我们可以在原始输入的上下、左右填充相同数量的行和列来保持空间维度
    2. 对于任何二维张量 X \mathbf{X} X,当所有边的填充行列数相同且输出保持空间维度时,输出 Y [ i , j ] \mathbf{Y}[i, j] Y[i,j] 是通过以输入 X [ i , j ] \mathbf{X}[i, j] X[i,j] 为中心,与卷积核进行互相关计算得到的
  • 下面给出两个例子
    1. 创建一个高度和宽度为3的二维卷积层,并在所有侧边填充1个像素(上下共填充2 / 左右共填充2)。给定高度和宽度为8的输入,则输出的高度和宽度也是8
      import torch
      from torch import nn# 为了方便起见,我们定义了一个计算卷积层的函数。
      # 此函数初始化卷积层权重,并对输入和输出提高和缩减相应的维数
      def comp_conv2d(conv2d, X):# 这里的(1,1)表示批量大小和通道数都是1X = X.reshape((1, 1) + X.shape)Y = conv2d(X)# 省略前两个维度:批量大小和通道return Y.reshape(Y.shape[2:])# 请注意,这里每边都填充了1行或1列,因此总共添加了2行或2列
      conv2d = nn.Conv2d(1, 1, kernel_size=3, padding=1)
      X = torch.rand(size=(8, 8))
      comp_conv2d(conv2d, X).shape
      
      >>> torch.Size([8, 8])
      
    2. 我们使用高度为 5,宽度为 3 的卷积核,高度和宽度两边的填充分别为2(共4)和1(共2)
      conv2d = nn.Conv2d(1, 1, kernel_size=(5, 3), padding=(2, 1))
      comp_conv2d(conv2d, X).shape
      
      >>> torch.Size([8, 8])
      

3.2 步幅

  • 在计算互相关时,卷积窗口从输入张量的左上角开始,向下、向右滑动。 在前面的例子中,我们默认每次滑动一个元素。 但是,有时候为了高效计算或是缩减采样次数,卷积窗口可以跳过中间位置,每次滑动多个元素

  • 我们将每次滑动元素的数量称为步幅stride,下图显示了垂直步幅为3,水平步幅为2的二维互相关运算。着色部分是输出元素以及用于输出计算的输入和内核张量元素
    在这里插入图片描述
    通常,当垂直步幅为 s h s_h sh、水平步幅为 s w s_w sw 时,输出形状为
    ⌊ ( n h − k h + p h + s h ) / s h ⌋ × ⌊ ( n w − k w + p w + s w ) / s w ⌋ . \left\lfloor\left(n_{h}-k_{h}+p_{h}+s_{h}\right) / s_{h}\right\rfloor \times\left\lfloor\left(n_{w}-k_{w}+p_{w}+s_{w}\right) / s_{w}\right\rfloor . (nhkh+ph+sh)/sh×(nwkw+pw+sw)/sw.

  • 下面给出一个例子,将高度和宽度的步幅设置为2,从而将输入的高度和宽度减半

    conv2d = nn.Conv2d(1, 1, kernel_size=3, padding=1, stride=2)
    comp_conv2d(conv2d, X).shape
    
    >>> torch.Size([4, 4])
    
  • 为了简洁起见,我们称填充为 ( p h , p w ) (p_h,p_w) (ph,pw),步幅为 ( s h , s w ) (s_h, s_w) (sh,sw)。特别地,当 p h = p w = p p_h=p_w=p ph=pw=p 时,称填充为 p p p;当 s h = s w = s s_h=s_w=s sh=sw=s 时,步幅是 s s s默认情况下,填充为0,步幅为1。实践中我们很少使用不一致的步幅或填充

4. 多输入多输出通道

  • 以上 2/3 节都是基于单个输入输出通道进行讨论的,这使得我们可以将输入、卷积核和输出看作二维张量。当添加通道时,输入和输出都变成了三维张量,本节将更深入地研究具有多输入和多输出通道的卷积核

4.1 多输入通道

  • 当输入包含多个通道时,需要构造一个与输入数据具有相同输入通道数的卷积核,以便与输入数据进行互相关运算。设输入数据尺寸为 ( c i , n h , n w ) (c_i, n_h,n_w) (ci,nh,nw),需要卷积核尺寸为 ( c i , k h , k w ) (c_i, k_h, k_w) (ci,kh,kw),这可以看作 c i c_i ci 个相同尺寸的卷积核,它们分别与输入的各个通道数据进行互相关运算得到 c i c_i ci 个二维输出,最后把它们按位置求和得到最终输出。如下图所示
    在这里插入图片描述

4.2 多输出通道

  • 在 1.4 节我们提到过,每个通道都向后续层提供一组空间化的学习特征,在最流行的神经网络架构中,随着神经网络层数的加深,我们常会增加输出通道的维数,通过减少空间分辨率以获得更大的通道深度
  • 通道有点类似 Transformer 中的多个注意力头,直观地说,我们可以将每个通道看作对不同特征的响应,但多输出通道并不仅是学习多个单通道的检测器,因为每个通道不是独立学习的,而是为了共同使用而优化的
  • c i , c o c_i,c_o ci,co 分别表示输入和输出的通道数量,用 k h , k w k_h,k_w kh,kw 表示卷积核的高度和宽度,为了获得多个通道的输出,我们可以为每个输出通道创建一个形状为 ( c i , k h , k w ) (c_i, k_h, k_w) (ci,kh,kw) 的卷积核张量,这样卷积核的最终形状为 ( c o , c i , k h , k w ) (c_o, c_i, k_h, k_w) (co,ci,kh,kw)在互相关运算中,每个输出通道先获取所有输入通道,再以对应该输出通道的卷积核计算出结果

4.3 只作用在通道上的 1X1 卷积层

  • k h = k w = 1 k_h=k_w=1 kh=kw=1 时,卷积核只能输入一个空间位置的像素,这种卷积核不再能提取相邻像素间的相关特征,它唯一的计算发生在通道上,可以把 1x1 卷积看作在每个像素位置的所有通道上的全连接层,将 c i c_i ci 个输入转换为 c o c_o co 个输出,如下图所示
    在这里插入图片描述
  • 注意 1x1 卷积也是一个卷积层,故其跨像素的权重是一致的,权重维度为 c i × c o c_i\times c_o ci×co,再额外加上一个偏置

5. 汇聚层

  • 通常当我们处理图像时,我们希望逐渐降低隐藏表示的空间分辨率、聚集信息,这样随着我们在神经网络中层叠的上升,每个神经元对其敏感的感受野(输入)就越大。机器学习任务通常会跟全局图像的问题有关(例如,“图像是否包含一只猫呢?”),所以我们最后一层的神经元应该对整个输入的全局敏感,这需要我们逐渐聚合信息,生成越来越粗糙的映射
  • 现实中,随着拍摄角度的移动,任何物体几乎不可能发生在同一像素上,我们希望模型检查的底层特征(例如 2.1 节中讨论的边缘)保持某种程度上的平移不变性,前面介绍的卷积层相比全连接层已经具有更强的平移不变性了,汇聚层可以进一步增强模型的平移不变能力
  • 本节将介绍 汇聚/池化pooling 层,它具有双重目的
    1. 降低卷积层对位置的敏感性
    2. 降低对空间降采样表示的敏感性

5.1 最大汇聚层与平均汇聚层

  • 与卷积层类似,汇聚层运算符由一个固定形状的窗口组成,该窗口根据其步幅大小在输入的所有区域上滑动,为固定形状窗口(有时称为汇聚窗口)遍历的每个位置计算一个输出
  • 不同于卷积层中的输入与卷积核之间的互相关计算,汇聚层不包含参数。 相反,池运算是确定性的,通常有两种
    1. 最大汇聚层maximum pooling:计算汇聚窗口中所有元素的最大值
    2. 平均汇聚层average pooling:计算汇聚窗口中所有元素的平均值
  • 下图显示了最大汇聚层的处理过程
    在这里插入图片描述
    注意汇聚层的输入是卷积层的输出,我们可以假设上图中的输入 4 对应到原始图像输入上感受野的某个特征(随着层数叠加,感受野可以是较大的一片区间,特征也可以是高价的,比如鸟翅膀或猫尾巴),当原始图像输入发生少量平移时,以上汇聚层输入中的 4 可能偏移到左上角的 0 位置,最大汇聚层在这种情况下可以保持输出不变,这意味着更强的平移不变性

5.2 填充和步幅

  • 与卷积层一样,汇聚层也可以通过设置填充和步幅改变输出形状,pytorch 中语法如下
    # 定义卷积层,指定卷积核尺寸、填充和步幅
    conv2d = nn.Conv2D(1, kernel_size=(3, 5), padding=(0, 1), strides=(3, 4))# 定义最大池化层,指定汇聚窗口尺寸、填充和步幅
    pool2d = nn.MaxPool2d((2, 3), stride=(2, 3), padding=(0, 1))
    

5.3 多个通道

  • 在处理多通道输入数据时,汇聚层在每个输入通道上单独运算,而不是像卷积层一样在通道上对输入进行汇总,这意味着汇聚层的输出通道数与输入通道数相同
    import torch
    import numpy as npX = np.arange(16, dtype=np.float32).reshape((1, 1, 4, 4))
    X = np.concatenate((X, X + 1), 1)				# (1, 2, 4, 4)
    pool2d = nn.MaxPool2d(3, padding=1, stride=2)	# 由于汇聚层中没有参数,所以不需要调用初始化函数
    Y = pool2d(torch.tensor(X))                     # (1, 2, 2, 2)
    

6. 卷积神经网络

  • 一个完整的卷积神经网络通过交替堆叠卷积层和汇聚层提取图像特征,最后接全连接层调整维度,用于分类或回归任务。下面是经典 CNN 模型 LeNet 的结构图
    在这里插入图片描述
  • 考虑到篇幅问题,本文仅介绍 CNN 基础原理,各种经典模型的细节和 pytorch 实现将在后续其他文章介绍,链接将更新到此处。To be continue…

这篇关于经典机器学习方法(7)—— 卷积神经网络CNN的文章就介绍到这儿,希望我们推荐的文章对编程师们有所帮助!



http://www.chinasem.cn/article/1084821

相关文章

51单片机学习记录———定时器

文章目录 前言一、定时器介绍二、STC89C52定时器资源三、定时器框图四、定时器模式五、定时器相关寄存器六、定时器练习 前言 一个学习嵌入式的小白~ 有问题评论区或私信指出~ 提示:以下是本篇文章正文内容,下面案例可供参考 一、定时器介绍 定时器介绍:51单片机的定时器属于单片机的内部资源,其电路的连接和运转均在单片机内部完成。 定时器作用: 1.用于计数系统,可

问题:第一次世界大战的起止时间是 #其他#学习方法#微信

问题:第一次世界大战的起止时间是 A.1913 ~1918 年 B.1913 ~1918 年 C.1914 ~1918 年 D.1914 ~1919 年 参考答案如图所示

[word] word设置上标快捷键 #学习方法#其他#媒体

word设置上标快捷键 办公中,少不了使用word,这个是大家必备的软件,今天给大家分享word设置上标快捷键,希望在办公中能帮到您! 1、添加上标 在录入一些公式,或者是化学产品时,需要添加上标内容,按下快捷键Ctrl+shift++就能将需要的内容设置为上标符号。 word设置上标快捷键的方法就是以上内容了,需要的小伙伴都可以试一试呢!

AssetBundle学习笔记

AssetBundle是unity自定义的资源格式,通过调用引擎的资源打包接口对资源进行打包成.assetbundle格式的资源包。本文介绍了AssetBundle的生成,使用,加载,卸载以及Unity资源更新的一个基本步骤。 目录 1.定义: 2.AssetBundle的生成: 1)设置AssetBundle包的属性——通过编辑器界面 补充:分组策略 2)调用引擎接口API

Javascript高级程序设计(第四版)--学习记录之变量、内存

原始值与引用值 原始值:简单的数据即基础数据类型,按值访问。 引用值:由多个值构成的对象即复杂数据类型,按引用访问。 动态属性 对于引用值而言,可以随时添加、修改和删除其属性和方法。 let person = new Object();person.name = 'Jason';person.age = 42;console.log(person.name,person.age);//'J

大学湖北中医药大学法医学试题及答案,分享几个实用搜题和学习工具 #微信#学习方法#职场发展

今天分享拥有拍照搜题、文字搜题、语音搜题、多重搜题等搜题模式,可以快速查找问题解析,加深对题目答案的理解。 1.快练题 这是一个网站 找题的网站海量题库,在线搜题,快速刷题~为您提供百万优质题库,直接搜索题库名称,支持多种刷题模式:顺序练习、语音听题、本地搜题、顺序阅读、模拟考试、组卷考试、赶快下载吧! 2.彩虹搜题 这是个老公众号了 支持手写输入,截图搜题,详细步骤,解题必备

电脑不小心删除的文件怎么恢复?4个必备恢复方法!

“刚刚在对电脑里的某些垃圾文件进行清理时,我一不小心误删了比较重要的数据。这些误删的数据还有机会恢复吗?希望大家帮帮我,非常感谢!” 在这个数字化飞速发展的时代,电脑早已成为我们日常生活和工作中不可或缺的一部分。然而,就像生活中的小插曲一样,有时我们可能会在不经意间犯下一些小错误,比如不小心删除了重要的文件。 当那份文件消失在眼前,仿佛被时间吞噬,我们不禁会心生焦虑。但别担心,就像每个问题

《offer来了》第二章学习笔记

1.集合 Java四种集合:List、Queue、Set和Map 1.1.List:可重复 有序的Collection ArrayList: 基于数组实现,增删慢,查询快,线程不安全 Vector: 基于数组实现,增删慢,查询快,线程安全 LinkedList: 基于双向链实现,增删快,查询慢,线程不安全 1.2.Queue:队列 ArrayBlockingQueue:

YOLOv8改进 | SPPF | 具有多尺度带孔卷积层的ASPP【CVPR2018】

💡💡💡本专栏所有程序均经过测试,可成功执行💡💡💡 专栏目录 :《YOLOv8改进有效涨点》专栏介绍 & 专栏目录 | 目前已有40+篇内容,内含各种Head检测头、损失函数Loss、Backbone、Neck、NMS等创新点改进——点击即可跳转 Atrous Spatial Pyramid Pooling (ASPP) 是一种在深度学习框架中用于语义分割的网络结构,它旨

硬件基础知识——自学习梳理

计算机存储分为闪存和永久性存储。 硬盘(永久存储)主要分为机械磁盘和固态硬盘。 机械磁盘主要靠磁颗粒的正负极方向来存储0或1,且机械磁盘没有使用寿命。 固态硬盘就有使用寿命了,大概支持30w次的读写操作。 闪存使用的是电容进行存储,断电数据就没了。 器件之间传输bit数据在总线上是一个一个传输的,因为通过电压传输(电流不稳定),但是电压属于电势能,所以可以叠加互相干扰,这也就是硬盘,U盘