卷积神经网络的发展历史(超详细介绍)
:是一种前馈神经网络,最早可追溯到1986年的BP算法。
- 三大网络结构:卷积层(Conv2d)、池化层(MaxPool2d)、全连接层(Linear)
- 两大特点:稀疏连接、权值共享。可以用更少的参数,获得更高的性能。
下面是一个简单的CNN模型:
Python实现上述模型:
函数定义详解:Pytorch之(__ call__)、( __ init__)、(forward)
作用:实现信息的前向传导。
过程:将数据从输入层,依次经过多个隐藏层(如果有),最终到达输出层。其中,数据每经过一个网络层,其节点输出的值所代表的信息层次就越高阶和概括。
例如:人脸识别。
- (1)输入图像:每个像素值,只表示灰度值;
- (2)经过第一个网络层:(可能)第二层中每个节点输出的值,表示边缘特征(如:脸部轮廓);
- (3)经过第二个网络层:(可能)第三层中每个节点输出的值,表示局部特征(如:鼻子、眼睛);
- (4)最后输出层:表示网络对输入图像的判断结果,即是否是一张人脸。
备注:节点中输出的值是通过与其相连的前一层中所有的节点输出值的加权求和处理后的结果。
卷积神经网络的核心网络层是卷积层,而卷积层的核心是卷积。
2.1.1、卷积运算 —— 提取特征
卷积运算就是互相关( cross-correlation )运算。
:中的 2 分别乘以中的每个值,然后卷积结果。
其中,输入、输出和卷积核都是张量,卷积核(kernel)又叫权重过滤器,简称过滤器(Filter)。
卷积运算公式
(1)假设输入图像大小是,卷积核大小是,补0的圈数为,步长为,卷积后输出特征图大小为。
(2)图像高度和宽度的计算公式:
备注:若输入图像为 m x n,想要转换为 m x m 或 n x n 的图像,则可以采用裁剪、拼接、填充的方法。
2.1.2、稀疏连接 —— 降低了模型的复杂度,防止过拟合
【输入条件】:(1)输入单通道图像大小 3 x 3;(2)卷积核大小 2 x 2;
【分析说明】
- 卷积运算的详细过程:(1)取(3 x 3)输入图像中的(2 x 2)矩阵,然后与(2 x 2)卷积核进行卷积运算,得到一个计算结果( );(2)通过滑窗,循环计算得到输出特征图(2 x 2)。
【结论】:稀疏连接相比于全连接,大大缩减了权重参数数量,也极大避免了过拟合。
2.1.3、权值共享 —— 减少权值数量,模型易优化
输入图像
- (1)输入彩色图像;其中,3表示RGB三个通道
- (2)卷积层的卷积核个数为,,即。
卷积运算(多通道)
结论:
(0)权值共享:大大减少了模型的权重参数。
(1)权值共享:当前隐藏层中的所有神经元都在检测图像不同位置的同一个特征,即检测特征相同。因此也将输入层到隐藏层的这种映射称为特征映射。
(2)多个卷积核分别用于识别图像不同位置的特征。通过全连接层将所有特征整合,输出一个值(猫 / 狗)。
2.1.4、权值初始化 —— 决定算法是否收敛
(1)深度学习为何要初始化? —— 影响算法结果
- 深度学习算法:由于
- 机器学习算法:影响小。
(2)初始化对训练的影响?—— 决定算法是否收敛
- (1)若参数太大,将导致在前向传播或反向传播中产生爆炸的值;
- (2)若参数太小,将导致信息丢失;
- (3)适当的参数初始化,能加快收敛速度。
- 采用启发式的方法挑选常数,进而设置每个单元的偏置。
- 实验表明:正态分布初始化(高斯分布)、正交分布初始化、均匀分布初始化的效果更好。
- 权重初始化的方法:零值初始化、随机初始化、均匀分布初始化、正态分布初始化和正交分布初始化等。
2.1.5、感受野 —— 在原始图像上映射的区域大小
:每个网络层的输出特征图上的像素点,在原始图像上映射的区域大小。
注意1:感受野的计算不考虑" 边界填充 " 。
注意2:最后一层(卷积层或池化层)输出特征图的感受野大小等于卷积核的大小。
注意3:第(i)层卷积层的感受野大小和卷积核大小,与步长、第(i+1)层的感受野大小都有关。
详细计算过程:根据卷积得到的最后一层感受野,反算前一层感受野,然后循环且逐层的传递到第一层。
公式如下:
- 【举例1】:。其中,卷积核的步长为1、padding为0。
计算如下:(1-1)* 1+3 = 3 => (3-1)*1+3 = 5
- 【举例2】:。其中,卷积核的步长为1,padding为0。
计算如下:(1-1)* 1+3 = 3 => (3-1)*1+3 = 5 => (5-1)*1+3 = 7
- 【举例3】:神经网络
❤️ 感受野与卷积核的关系,是否卷积核越大越好?
- 如果堆叠3个3 * 3的卷积核,并且保持步长为1,其感受野等于7 * 7;那么这和直接使用7 * 7卷积核的结果是一样的,为什么要如此麻烦呢?
2.1.6、边界填充Padding —— 图像尺寸对齐,保持边界信息
padding=1:表示在输入图像的边界填充 1 圈,全 0 元素。
作用:
- (1)图像尺寸对齐:对图像进行扩展,扩展区域补零。
- (2)保持边界信息:若没有padding,卷积核将对输入图像的边界像素只卷积一次,而中间像素卷积多次,导致边界信息丢失。
假设输入图像大小是 input x input,卷积核大小是 kernel,步长为stride,补0的圈数为padding。
Python深度学习pytorch神经网络填充和步幅的理解
(1)用于神经网络的隐含层与输出层之间(如:卷积层+激活函数+池化层),为神经网络提供非线性建模能力。
(2)若没有激励函数,则模型只能处理线性可分问题。与最原始的感知机相当,拟合能力有限。
:一条直线将图像A中的蓝点和绿点完全分开(最理想、最简单的二分类问题)
:一条封闭曲线将图像B中的蓝点和绿点完全分开
深度学习的四种激活函数:PyTorch中激活函数的方法示例
如何选择激活函数:
- (1):若网络层数不多
- (2):若网络层数较多
- 不宜选择sigmoid、tanh,因为它们的导数都小于1,sigmoid的导数更是在[0, 1/4]之间。
- 根据微积分链式法则,随着网络层数增加,导数或偏导将指数级变小。
- 所以,网络层数较多的激活函数其导数不宜小于1也不能大于1,大于1将导致梯度爆炸,导数为1最好,而relu正好满足这个要求。
- (3):用于多分类神经网络输出层。一分钟理解softmax函数(超简单)
为什么要进行池化操作?
- 通过卷积层获得的图像特征,可以直接训练分类,但很容易导致过拟合。
:又叫下采样、降采样。
作用: 降采样(减少参数),增大感受野,提高运算速度及减小噪声影响,防止过拟合。
分类:
- (1)局部池化
- (2)全局池化
备注:全局池化相比局部池化能减少更多参数,且泛化能力比较好,但唯一的不足之处是收敛速度比较慢。
Python:池化的用法及代码(示例)
全连接层(Fully Connected Layers,FC):
- —— 将原始数据映射到隐层特征空间,提取特征;
- —— 将学到的 “分布式特征” 映射到样本标记空间,进行分类;
全连接层FC的缺点:
- (1)由于忽略了空间结构,故不适用于目标检测。如:分割任务中的FCN采用卷积层替换全连接层。
- (2)全连接层的参数过多,导致模型复杂度提升,容易过拟合。如:ResNet、GoogleNet采用全局平均池化替换全连接层。
全连接层中的每个神经元都可以看成是一个加权平均且不带偏置的多项式。可以简单写成:y = W * x。
全连接层FC的作用:这一步卷积还有一个非常重要的作用,就是将分布式特征representation映射到样本标记空间。简单来说,就是将输入图像的所有特征整合到一起,输出一个值(猫 / 狗)。
效果:
下张图是上面任意一张图的图解:
由图可得:
- (1)猫虽然在不同的位置输出的特征值相同,但可能分类结果不同。
- (2)全连接层FC:忽略了空间结构特性。即目标不管在什么位置,只要图像中有这个猫,那么就能判断它是猫。
作用:迭代训练,降低损失(loss)
介绍:与最优化方法(如:梯度下降法)结合使用的,用来训练神经网络的常见方法。
计算过程:通过损失函数,计算模型中所有权重参数的梯度,并反馈给优化算法进行梯度(权值)更新。迭代训练 N 次,获得最小损失。
单次反向传播的过程:首先是离输出层最近的,然后是,并按照的依次顺序进行反向传播,直到所有层都完成一次。
损失函数:用来衡量模型预测值与真实值之间的差异。
- 损失函数越小说明模型和参数越符合训练样本。
- 任何能够衡量模型预测值与真实值之间差异的函数都可以叫做损失函数。
- 为了避免过拟合,一般在损失函数的后面添加正则化项:。
常用的损失函数:
:对于减少测试误差的方法的统称。
作用: 降低模型的复杂度,减少模型对训练样本的依赖度,提升模型的泛化能力,防止过拟合。
思路:在损失函数的后面添加一个惩罚项。
作用:正则化系数 λ :控制模型的可学习参数,防止过拟合。
计算过程(求解线性模型):找到一个 θ 值,然后对 J(θ) 进行求导,使得代价函数 J(x) 取得最小值(导数为0)。
常用的惩罚项:L1正则化、L2正则化、Dropout正则化
- 在机器学习的线性回归模型中,使用L1正则化得到的模型叫Lasso模型,使用L2正则化得到的模型叫岭回归(Ridge regression)。
3.2.1、L1正则化(特征选择) —— 冗余参数置零
- 特点:又叫特征选择,产生稀疏权值矩阵。即提取权重值最大的前N个值,并将冗余的权重值置0,直接删除。
3.2.2、L2正则化(权重衰减) —— 过拟合参数趋近于0
- 特点:又叫权重衰减。即抑制模型中产生过拟合的参数,使其趋近于0(而不等于0),影响变小。
- 特点:倾向于让所有参数的权值尽可能小。
若不关心显式特征(哪些特征重要或不重要),L2正则化的性能往往优于L1正则化。
3.2.3、Dropout正则化 —— 随机删除一定比例的神经元
- 一般只在训练阶段使用,测试阶段不使用。
- 一般控制在20% ~ 50%。太低没有效果,太高则会导致模型欠学习。
应用场景:
(1)在大型网络模型上效果显著
(2)在输入层和隐藏层都使用Dropout
(3)当学习率和冲量值较大时:如学习率扩大10 ~ 100倍,冲量值调高到0.9 ~ 0.99。
(4)用于限制网络模型的权重时:学习率越大,权重值越大。
:通过优化策略(梯度下降)来更新可学习参数(权值W和偏置bias),使得损失函数Loss值逐步降低,输出的模型更接近真实标签。
影响因素:(1)梯度方向(2)学习率
常用优化器:
- 00、经典的梯度下降法。
- 11、梯度下降优化算法:SGD、SGDM、NAG
缺点:缓解了参数空间的方向问题,但需要新增参数,且对学习率的控制也不太理想。- 22、自适应优化算法:AdaGrad(累积梯度平方)、RMSProp(累积梯度平方的滑动平均)、Adam(带动量项的RMSProp)
而自适应优化算法,学习率不再是一个固定不贬值,它会根据实际情况自动调整以适应环境。
3.3.1、梯度下降 —— 使得loss值逐步降低
梯度下降的公式如下图:
其中:
θ(t+1):表示参数θ在t+1次迭代时需要更新的参数;
θ(t):表示参数θ在第t次迭代时更新的参数值;
J(θt):表示目标函数(损失函数)在θ(t)该点上的梯度;
lr:表示学习率。其控制参数更新速度以及模型学习速度。
梯度下降:沿着目标函数梯度的反方向搜索极小值。
梯度下降算法原理讲解
- 计算:每次迭代过程中,采用所有的训练数据的平均损失来近似目标函数。
- 特点:(1)靠近极值点时收敛速度减慢;(2)可能会" 之 "字形的下降。(3)对学习率非常敏感,难以驾驭;(4)对参数空间的方向没有解决方法。
- 左图一 学习率过小,将导致收敛速度慢,耗时长;
- 中图二 当学习率取值恰当时,可以收敛到全面最优点(凸函数)或局部最优点(非凸函数)。
- 右图三 学习率过大,将导致越过极值点(如:在平坦的区域,因梯度接近于0,可能导致训练提前终止)
备注: 可能出现在迭代过程中保持不变,容易造成算法被卡在鞍点的位置。
3.3.2、SGD、SGDM、NAG
3.3.3、AdaGrad、RMSProp、Adam
不同优化算法(理论推导)
MNIST数据集:多种优化器的收敛效果对比
:用于控制权重参数的学习速度。一般情况下,学习率随着epoch的增大而逐渐减小,可以达到更好的训练效果。
为什么加入学习率?
- (1)神经网络通过梯度下降+反向传播进行参数更新。
- 主要流程:将可学习参数(权值W和偏置bias)反向传播给网络层,使得损失函数Loss值逐步降低,输出的模型更接近真实标签。
- (2)神经网络在参数学习过程中,需要多轮训练,而每一论训练得到的可学习参数,需要通过学习率来控制学习速度,使得下一轮训练时的损失更小,最终达到最优模型。
3.4.1、自定义更新学习率(根据epoch)
3.4.2、动态调整学习率:torch.optim.lr_scheduler
- Pytorch官网:torch.optim.lr_scheduler 动态调整学习率
- torch.optim.lr_scheduler:调整学习率(详解)
(1)模型训练 + 模型验证
(2)保存模型 + 加载模型 + 加载模型的状态字典
(3)模型测试(可视化结果)
超参数:影响网络模型的性能。通过参数调整(调参),以寻找模型的全局最优解。
- 调参是一门技术活。
- 超参数是模型训练前设置的模型参数,而不是训练后得到的参数。
5.1.1、超参数 —— Epoch
:将整个训练集在模型上完成一次训练的过程,包括前向传播和反向传播。
:实现模型的迭代学习,充分学习数据集中的特征并提高性能,直到收敛到最佳性能或达到停止条件。
- 在训练过程中,可以根据模型的性能和训练效果来决定训练的 Epoch 数量。
- 通常情况下,Epoch 数量越多,模型的性能可能会越好,但也可能会导致过拟合的问题。因此,在选择 Epoch 数量时需要进行适当的调整和权衡。
5.1.2、超参数 —— Batch Size
:在训练过程中,每次输入模型的样本数量。
- batch_size 经验值 = 8、16、32、64、128 等等 —— (GPU对 2 的幂次的 batch 可以发挥更佳的性能)
- 影响因素:整个训练集大小、硬件资源、训练速度、收敛速度和模型稳定性等
- 如何选择最优的 Batch Size ? (具体问题具体分析)测试不同的 batch_size,并根据测试结果不同调整,从而找到适合当前任务的最佳设置。
Batch Size:决定了梯度下降的方向。
- 训练速度提升:使用GPU多线程并行处理,加速参数更新过程,直到达到时间最优。
- 前提:显卡显存支持,否则明显减慢。 —— 若超过显存(专用 GPU 内存),则超出部分转移到(共享 GPU 内存),此时速度会明显减慢。
- 若(创建和销毁线程的时间开销)小于(将Batch_size数据从CPU上传到GPU),则加速,反之减速。
- 收敛速度变慢:导致梯度估计的不准确性和方差较大,使得模型需要更多的 Epoch 来收敛到较优的解。
- 泛化性能增强:提供更多的样本信息来估计梯度,使得模型更容易学习数据集的特征,并提高泛化性能。而较小的 batch-size 下更易受到噪声影响。
- 最终收敛精度提升:可以减少梯度的方差,使得参数更新的方向更加稳定,从而更容易收敛到较优的解。
5.1.3、超参数 —— Epoch、Batch Size、Patch的关系
(1)在模型训练过程中,通常将整个训练集完成多次迭代训练;
(2)每一次训练通常将整个数据集划分为若干个批次(每个批次包含多个样本),然后每次输入一个批次数据到模型中。
(3)每个批次数据在输入模型训练之前,通常采用图像预处理(灰度化 + 归一化 + 去噪 + 裁剪等等)。
- :表示将整个训练集在模型中的完成一次训练的过程;
- 在每个Epoch中,通常都会采用 " 数据集随机打乱 " 的策略,提高模型的泛化能力。
- :表示每次输入到模型的样本数量;
- 如:训练集样本数 = 500,Batch Size = 32,共得到 batches = (500/64) = 7.8125。
- 在Pytorch数据加载器中,可以选择是否丢弃最后一个不足Batch Size的样本,若不丢弃则最后一个训练集样本数量 = 0.8125 * 64 = 52。
- 用于提高训练效率。
- :表示一幅图像中的一个子区域;
- 如:图像尺寸 = 256 x 256,patch = 64 x 64,重叠率overlap = 0,共得到 patches = (256/64)x(256/64)= 16。
- (数据增强)用于局部特征的学习,从而更好地理解整体图像。
5.1.4、影响因素:时耗
5.2.1、数据分配:训练集 + 验证集 + 测试集
- (1)训练集、验证集、测试集(比例为8 : 1 : 1),用于防止模型过拟合。
- (2)若没有验证集,则训练集与验证集的划分比例为7 : 3。
备注:如果把测试集当做验证集,通过调参去拟合测试集,等于在作弊。
5.2.2、数据增强(Data Augmentation)
在现有数据集下,通过数据增强扩增 N 倍的训练集,而不增加额外数据集,从而实现大样本训练。
- 作用一:扩大训练集,降低模型对某些属性的依赖,提高模型的泛化能力。
- 作用二:减少模型对物体位置的依赖性,并降低模型对色彩的敏感度等。
- 如:CNN物体分类,不会因为其位置、角度、大小、照明等(或以上的组合)而发生改变,因此CNN具有不变性属性。
torchvision.transforms:图像变换
5.2.3、归一化 + 标准化 + 正态分布
标准化:既是归一化也是正态分布。
❤️ :将数据范围归整到(0,1)或(-1,1)之间的小数。
- Min-Max 归一化
- ( 0,1):
- (-1,1):
❤️ :具有均值为0,标准差为1的标准正态分布,取值范围 (+∞,−∞)。
- 均值标准化(Z-score standardization):
❤️ ,又名高斯分布(Gaussian distribution)。
- μ:均数,决定了正态分布的位置。
- 与μ越近,被取到的概率就越大,反之越小。
- σ:标准差,表示正态分布的离散程度。
- σ越大,数据分布越分散,曲线越扁平;
- σ越小,数据分布越集中,曲线越陡峭。
- 正态分布是一种概率分布。曲线与横轴之间的面积恒等于1。
- 正态分布的曲线特征:以均数为中心,左右对称,且曲线的两端无限趋近于横轴,但永不相交。
- —— 记为
- —— 记为
5.3.0、项目开发 - 使用指南
在开发或复现一个开源项目时,需要注意几个核心问题:
- (1)在训练集上,若模型的训练结果具有与给定标签95%以上的匹配度,则证明当前模型的学习能力没有问题;
- 验证方法:在迭代训练过程中,打印 / 保存每个 epoch 的预测结果,并观察结果是否越来越好(个别异常不影响)以及最后的预测结果是否符合要求。
- (2)通常来说,网络模型的设计框架才是深度学习的核心,而图像前处理主要用于数据的泛化性,所以不需要过于复杂。(如:UNet模型)
- 数据的泛化性就是解决训练集的尺度不一致、数据类型不一致等问题;
- 训练和测试必须保持一致的图像前处理。
- 具有泛化性的图像前处理包括:全局归一化、随机裁剪patch等等。
- (3)在测试集上,测试是否具有泛化性
- 核心:必须知道算法的内部实现逻辑、函数的输入参数 + 输出结果,算法对数据的像素级变化等等
- 简单算法:可以直接调用(如:cv2.size等)
- 复杂算法:最好自己敲代码实现(如:rollingball等)
例如:
- 图像归一化(归一化到0~255是否有截断?等等)
- 冗余的图像处理操作???
- 冗余的超参数设置???
标准的开源项目具有以下几个特点:清晰的架构设计、明确的执行流程、经过优化且逻辑的算法。
github:Pytorch-UNet
github:nnUNet
Segment Anything
网络模型:__ init __ 、forward
类函数:__ init 、 len 、 getitem __
网络模型:__ init __ 、forward
类函数:__ init 、 len 、 getitem __
5.3.1、过拟合 + 欠拟合
❤️ 模型的泛化性:用于衡量训练集与测试集之间的误差。若相差无几,则模型具有泛化性,反之亦然。
:训练集与测试集的准确率都低
- 原因:(1)训练样本数量少;(2)模型复杂度太低;(3)参数还未收敛就停止循环;
- 解决办法:
- (1)增加样本数量
- (2)增加权重参数
- (3)提高模型复杂度
- (4)增加训练次数
- (5)查看是否是学习率过高导致模型无法收敛;
:训练集的准确率高,而测试集的准确率低,泛化能力差。
- 原因:(1)数据的噪声太大;(2)权重参数太多;(3)模型太复杂无法收敛。
- 解决办法:
- (1)数据预处理,剔除冗余特征的样本数据;
- (2)减少权重参数,避免学习冗余特征;
- (3)降低模型复杂度,避免学习冗余特征;
- (4)添加Dropout,避免对特定权重参数的依赖性;
- (5)降低L2正则化参数,降低权重参数的影响;
- (6)数据归一化,消除权重参数 W 的缩放影响。
5.3.2、梯度消失 + 梯度爆炸 —— 解决方法:激活函数 + BN批标准化
:激活函数求导后,与权重参数 W 相乘后的结果。
- 梯度爆炸(gradient > 1):当层数增多,梯度以指数形式增加,使得参数无法确定更新方向,导致无法优化代价函数。
- 梯度消失(gradient < 1):当层数增多,梯度以指数形式衰减。使得参数一下子跳过最优点,导致学习过程极不稳定。
如何解决梯度消失和梯度爆炸:
- (1)合理选择激活函数:常用激活函数(简介+图解+导数):Sigmoid、Tanh、ReLU、LReLU、RReLU、ELU
- sigmoid梯度随着x的增大或减小和消失,而ReLU不会
- sigmoid导数的取值范围为[0, 0.25],而ReLU导数的取值范围为[0, 1]。
- (2)BN批标准化(Batch Normalization):
- 标准化处理每一层的输出信号,进而消除权重参数 W 的缩放影响
5.3.3、区别:model.train() + model.eval()
【Pytorch】model.train()和model.eval()用法和区别,以及model.eval()和torch.no_grad()的区别
Pytorch控制模型状态的两个方法:
备注:在训练过程中,模型需要保持两种状态的切换,以确保在不同阶段获得正确的行为。
5.3.4、保存模型 + 加载模型 + 加载模型的状态字典
到此这篇cnn神经网络(CNN神经网络预测实例)的文章就介绍到这了,更多相关内容请继续浏览下面的相关推荐文章,希望大家都能在编程的领域有一番成就!
- torchvision.models:提供预训练模型下载
- torch.load() + torch.save() + model.state_dict() + model.load_state_dict()
版权声明:
本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。
如若内容造成侵权、违法违规、事实不符,请将相关资料发送至xkadmin@xkablog.com进行投诉反馈,一经查实,立即处理!
转载请注明出处,原文链接:https://www.xkablog.com/cjjbc/69972.html