赞
踩
在学习了上一节数据层中的参数详解后,本文内容讲主要讲述Caffe网络模型中隐藏层的独有的参数信息(name, type, bottom, top和transform_param是所有层共有参数)。
卷积层是卷积神经网络(CNN)的核心层,但在这之前希望你了解卷积操作。
拓展:在Pytorch中主要是通过nn.Conv2d(input_ch,output_ch,kernelsize,stride,padding)来实现的与Caffe中实现的原理一致。
层类型:Convolution
lr_mult: 学习率的系数,最终的学习率是这个数乘以solver.prototxt配置文件中的base_lr。如果有两个lr_mult, 则第一个表示权值的学习率,第二个表示偏置项的学习率。一般偏置项的学习率是权值学习率的两倍。--表示该层的学习率
在后面的convolution_param中,我们可以设定卷积层的特有参数。
必须设置的参数:
num_output: 卷积核(filter)的个数
kernel_size: 卷积核的大小。如果卷积核的长和宽不等,需要用kernel_h和kernel_w分别设定
其它参数:
stride: 卷积核的步长,默认为1。也可以用stride_h和stride_w来设置。
pad: 扩充边缘,默认为0,不扩充。 扩充的时候是左右、上下对称的,比如卷积核的大小为5*5,那么pad设置为2,则四个边缘都扩充2个像素,即宽度和高度都扩充了4个像素,这样卷积运算之后的特征图就不会变小。也可以通过pad_h和pad_w来分别设定。
weight_filler: 权值初始化。 默认为“constant",值全为0,很多时候我们用"xavier"算法来进行初始化,也可以设置为”gaussian"
bias_filler: 偏置项的初始化。一般设置为"constant",值全为0。
bias_term: 是否开启偏置项,默认为true, 开启
group: 分组,默认为1组。如果大于1,我们限制卷积的连接操作在一个子集内。如果我们根据图像的通道来分组,那么第i个输出分组只能与第i个输入分组进行连接。
输出层size计算公式
示例:
- layer {
- name: "conv1"
- type: "Convolution"
- bottom: "data"
- top: "conv1"
- param {
- lr_mult: 1 #lr_mult: 学习率的系数,最终的学习率是这个数乘以solver.prototxt配置文件中的base_lr。如果有两个lr_mult, 则第一个表示权值的学习率,第二个表示偏置项的学习率。一般偏置项的学习率是权值学习率的两倍。
- }
- param {
- lr_mult: 2
- }
- convolution_param {
- num_output: 20 #卷积核(filter)的个数
- kernel_size: 5 #卷积核的大小
- stride: 1 #卷积核的步长,默认为1
- pad: 0 #扩充边缘,默认为0,不扩充
- weight_filler {
- type: "xavier" #权值初始化。 默认为“constant",值全为0,很多时候我们用"xavier"算法来进行初始化,也可以设置为”gaussian"
- }
- bias_filler {
- type: "constant" #偏置项的初始化。一般设置为"constant",值全为0
- }
- }
- }
也叫池化层,为了减少运算量和数据维度而设置的一种层。在Pytorch中使用MaxPool2d或者AvgPool2d等方法来实现。
层类型:Pooling
必须设置的参数:
kernel_size: 池化的核大小。也可以用kernel_h和kernel_w分别设定。
其它参数:
pool: 池化方法,默认为MAX。目前可用的方法有MAX, AVE, 或STOCHASTIC
pad: 和卷积层的pad的一样,进行边缘扩充。默认为0
*stride: 池化的步长,默认为1。一般我们设置为2,即不重叠。也可以用stride_h和stride_w来设置。这个参数很重要,决定最终输出size的大小
示例:
- layer {
- name: "pool1"
- type: "Pooling"
- bottom: "conv1"
- top: "pool1"
- pooling_param {
- pool: MAX #池化方法,默认为MAX。目前可用的方法有MAX, AVE
- kernel_size: 3 #池化的核大小
- stride: 2 #池化的步长,默认为1。一般我们设置为2,即不重叠。
- }
- }
- #pooling层的运算方法基本是和卷积层是一样的。
- H1/C1=(h0/w0+2*pad-kernel_size)/stride+1;
对于激活函数,目前绝大多数论文中都是用的是ReLU,对于sigmoid,tanh等函数使用较少,详细对于可以参考我的这篇文章
f(x)=max(x,0)
- layer {
- name: "relu1"
- type: "ReLU"
- bottom: "pool1"
- top: "pool1"
- }
作用是在不改变数据的情况下,改变输入的维度和pytorch中x.view(x.view(0)[1],-1)用法相似,主要是对数据的维度进行调整。
有一个可选的参数组shape, 用于指定blob数据的各维的值(blob是一个四维的数据:[N,C,W,H])
dim:0 表示维度不变,即输入和输出是相同的维度。
dim:2 或 dim:3 将原来的维度变成2或3
dim:-1 表示由系统自动计算维度。数据的总量不变,系统会根据blob数据的其它三维来自动计算当前维的维度值 。
假设原数据为:32*3*28*28, 表示32张3通道的28*28的彩色图片
shape {
dim: 0
dim: 0
dim: 14
dim: -1
}
输出数据为:32*3*14*56
示例:
- layer {
- name: "reshape"
- type: "Reshape"
- bottom: "input"
- top: "output"
- reshape_param {
- shape {
- dim: 0 # copy the dimension from below
- dim: 2
- dim: 3
- dim: -1 # infer it from the other dimensions
- }
- }
- }
Dropout是一个防止过拟合的层,只需要设置一个dropout_ratio就可以了。
Dropout说的简单一点就是:我们在前向传播的时候,让某个神经元的激活值以一定的概率p停止工作,这样可以使模型泛化性更强,因为它不会太依赖某些局部的特征,如图1所示。
图1:使用Dropout的神经网络模型
2. Dropout工作流程及使用
2.1 Dropout具体工作流程
假设我们要训练这样一个神经网络,如图2所示。
图2:标准的神经网络
输入是x输出是y,正常的流程是:我们首先把x通过网络前向传播,然后把误差反向传播以决定如何更新参数让网络进行学习。使用Dropout之后,过程变成如下:
(1)首先随机(临时)删掉网络中一半的隐藏神经元,输入输出神经元保持不变(图3中虚线为部分临时被删除的神经元)
图3:部分临时被删除的神经元
(2) 然后把输入x通过修改后的网络前向传播,然后把得到的损失结果通过修改的网络反向传播。一小批训练样本执行完这个过程后,在没有被删除的神经元上按照随机梯度下降法更新对应的参数(w,b)。
(3)然后继续重复这一过程:
恢复被删掉的神经元(此时被删除的神经元保持原样,而没有被删除的神经元已经有所更新)
从隐藏层神经元中随机选择一个一半大小的子集临时删除掉(备份被删除神经元的参数)。
对一小批训练样本,先前向传播然后反向传播损失并根据随机梯度下降法更新参数(w,b) (没有被删除的那一部分参数得到更新,删除的神经元参数保持被删除前的结果)。
不断重复这一过程。
示例:
- layer {
- name: "drop7"
- type: "Dropout"
- bottom: "fc7-conv"
- top: "fc7-conv"
- dropout_param {
- dropout_ratio: 0.5
- }
- }
经过上一层的reshape操作一般会得到一个C*W*H 的一维向量,之后进行全连接,在Pytorch中使用nn.Linker进行实现,Caffe中实现方法如下。
- #全连接层,输出的是一个简单向量 参数跟卷积层一样
- layer {
- name: "ip1"
- type: "InnerProduct"
- bottom: "pool2"
- top: "ip1"
- param {
- lr_mult: 1
- }
- param {
- lr_mult: 2
- }
- inner_product_param {
- num_output: 500
- weight_filler {
- type: "xavier"
- }
- bias_filler {
- type: "constant"
- }
- }
- }
- #测试的时候输入准确率
- layer {
- name: "accuracy"
- type: "Accuracy"
- bottom: "ip2"
- bottom: "label"
- top: "accuracy"
- include {
- phase: TEST
- }
- }
之后用softmax输出各个label的confidence,softmax和softmax-loss的区别
softmax计算公式:
而softmax-loss计算公式:
- #softmax-loss layer:输出loss值
- layer {
- name: "loss"
- type: "SoftmaxWithLoss"
- bottom: "ip1"
- bottom: "label"
- top: "loss"
- }
-
- #softmax layer: 输出似然值
- layers {
- bottom: "cls3_fc"
- top: "prob"
- name: "prob"
- type: “Softmax"
- }
网络输出的结果,通过prob获取模型的最后输出,并进行后续的分类以及检测操作。
Copyright © 2003-2013 www.wpsshop.cn 版权所有,并保留所有权利。