前往小程序,Get更优阅读体验!
立即前往
首页
学习
活动
专区
工具
TVP
发布
社区首页 >专栏 >Caffe 中关于 LetNet-5 网络的定义文件 lenet.prototxt 解析

Caffe 中关于 LetNet-5 网络的定义文件 lenet.prototxt 解析

作者头像
用户1148525
发布2019-05-28 23:41:05
9150
发布2019-05-28 23:41:05
举报
文章被收录于专栏:机器学习、深度学习

版权声明:本文为博主原创文章,未经博主允许不得转载。 https://cloud.tencent.com/developer/article/1437721

https://github.com/BVLC/caffe/blob/master/examples/mnist 是Caffe关于LetNet-5的相关文件,

这里面有几个后缀是 .prototxt 的文件,它是用 protocol buffer 这个工具生成的文件。

百度百科对 protocol buffer 描述如下:

protocol buffer(以下简称PB)是google 的一种数据交换的格式,它独立于语言,独立于平台。Google 提供了多种语言的实现:java、c#、c++、go 和 python,每一种实现都包含了相应语言的编译器以及库文件。由于它是一种二进制的格式,比使用 xml 进行数据交换快许多。可以把它用于分布式应用之间的数据通信或者异构环境下的数据交换。作为一种效率和兼容性都很优秀的二进制数据传输格式,可以用于诸如网络传输、配置文件、数据存储等诸多领域。

Caffe 源码中大量使用 protocol buffer 作为权值和模型参数的载体。对于参数管理,我们拥有多种选择,有人喜欢 TXT 的易于修改,有人喜欢 BIN 的读写高效,也有人喜欢图形化配置的直观形象。不一致的参数管理带来很多问题。例如,一个项目组内不同成员必须约定一套统一的参数方案,或者称为通信协议,以便于模块集成。protocol buffer 工具完美的解决了这个问题,用户只需要建立统一的参数描述文件(proto),然后利用 protoc 编译就能让协议细节等关键部分代码自动生成,节省了大量的开发、调试时间。使用 protocol buffer 还可以跨语言(java、c#、c++、go 和 python)传递相同的数据结构,让团队协作更有效率。

下面我们来看看 Caffe 是如何定义和描述 LetNet-5 网络模型:

对于 LetNet-5 广义模型描述文件是 lenet.prototxt

下面我们来详细看看 lenet.prototxt :

代码语言:javascript
复制
// 输入层的定义:
 name: "LeNet" (网络的名字)
 layer {              (定义一个网络层)
   name: "data"    (网络层的名字为 data)
   type: "Input"   (网络层的类型,输入)
   top: "data"      (该网络层的输出叫 data )
   input_param { shape: { dim: 64 dim: 1 dim: 28 dim: 28 } }     }(64张图像为一批,28*28大小)
 }    
     (读取这批数据维度:64 1 28 28)

 // 第一卷积层的定义:    
 layer { 
   name: "conv1"     (网络层的名字为 conv1)
   type: "Convolution"   (网络层类型是 卷积层)
   bottom: "data"      (该层的输入层是 data 层)
   top: "conv1"      (该层的输出层叫 conv1 feature maps)
   param { 
     lr_mult: 1     (weights的学习率与全局相同)
   } 
   param { 
     lr_mult: 2     (biases的学习率是全局的2倍)
   } 
   convolution_param {      {(卷积操作参数设置)
     num_output: 20     (卷积输出数量20,由20个特征图Feature Map构成)
     kernel_size: 5      (卷积核的大小是5*5)
     stride: 1            (卷积操作步长)
     weight_filler { 
       type: "xavier"     (卷积滤波器的参数使用 xavier 方法来初始化)
     } 
     bias_filler { 
       type: "constant"     (bias使用0初始化)
     } 
   } 
 }    
     卷积之后这批数据维度:64 20 24 24

  // 第一池化层定义:  
 layer { 
   name: "pool1"    (网络层的名字是 pool1 )
   type: "Pooling"   (网络层的类型是 池化操作)
   bottom: "conv1"    (网络层的输入是 conv1 feature maps)
   top: "pool1"       (网络层的输出是 pool1)
   pooling_param {     (池化参数设置)
     pool: MAX          (最大池化操作)
     kernel_size: 2      (池化核尺寸,2*2 区域池化)
     stride: 2          (池化步长)
   } 
 } 
     池化之后这批数据维度:64 20 12 12

// 第二卷积层的定义:
 layer { 
   name: "conv2"   (该网络层的名字)
   type: "Convolution"  (该网络层的类型,卷积)
   bottom: "pool1"     (该网络层的输入是 pool1)
   top: "conv2"      (该网络层的输出是 conv2, feature maps)
   param { 
     lr_mult: 1      (weights的学习率与全局相同)
   } 
   param { 
     lr_mult: 2       (biases的学习率是全局的2倍)
   } 
   convolution_param {    (卷积参数设置)
     num_output: 50        (卷积的输出个数,由50个特征图Feature Map构成)
     kernel_size: 5        (卷积核尺寸 5*5)
     stride: 1              (卷积步长)
     weight_filler { 
       type: "xavier" 
     } 
     bias_filler { 
       type: "constant" 
     } 
   } 
 } 

卷积之后这批数据维度:64 50 8 8

// 第二池化层的定义:
 layer { 
   name: "pool2" 
   type: "Pooling" 
   bottom: "conv2" 
   top: "pool2" 
   pooling_param { 
     pool: MAX 
     kernel_size: 2 
     stride: 2 
   } 
 } 

池化之后这批数据维度:64 50 4 4

//  第一层全链接层的定义:
 layer { 
   name: "ip1"       (该网络层的名字 ip1)
   type: "InnerProduct"  (该网络层的类型是 全链接层)
   bottom: "pool2"    (该层的输入是 pool2)
   top: "ip1"          (该层的输出是 ip1)
   param { 
     lr_mult: 1 
   } 
   param { 
     lr_mult: 2 
   } 
   inner_product_param {    (全链接层的 参数设置)
     num_output: 500        (500个输出神经元)
     weight_filler { 
       type: "xavier" 
     } 
     bias_filler { 
       type: "constant" 
     } 
   } 
 } 
     500 个神经元

// 激活函数层的定义:
 layer { 
   name: "relu1"   (该网络层的名字 relu1) 
   type: "ReLU"     (该网络层的类型, ReLU 激活函数)
   bottom: "ip1"   (该层的输入是 ip1)
   top: "ip1"       (该层的输出还是 ip1,底层与顶层相同是为了减少开支)
} 

// 第二全链接层的定义:(数据的分类判断在这一层中完成)
layer { 
  name: "ip2" 
   type: "InnerProduct" 
   bottom: "ip1" 
   top: "ip2" 
   param { 
     lr_mult: 1 
   } 
   param { 
     lr_mult: 2 
   } 
   inner_product_param {    
     num_output: 10       (直接输出结果,0-9,十个数字所以维度是10)
     weight_filler { 
       type: "xavier" 
     } 
     bias_filler { 
       type: "constant" 
     } 
   } 
 } 

// 输出层的定义:
 layer { 
   name: "prob" 
   type: "Softmax"    (损失函数)
   bottom: "ip2" 
   top: "prob" 
 } 
本文参与 腾讯云自媒体同步曝光计划,分享自作者个人站点/博客。
原始发表:2016年12月12日,如有侵权请联系 cloudcommunity@tencent.com 删除

本文分享自 作者个人站点/博客 前往查看

如有侵权,请联系 cloudcommunity@tencent.com 删除。

本文参与 腾讯云自媒体同步曝光计划  ,欢迎热爱写作的你一起参与!

评论
登录后参与评论
0 条评论
热度
最新
推荐阅读
相关产品与服务
数据保险箱
数据保险箱(Cloud Data Coffer Service,CDCS)为您提供更高安全系数的企业核心数据存储服务。您可以通过自定义过期天数的方法删除数据,避免误删带来的损害,还可以将数据跨地域存储,防止一些不可抗因素导致的数据丢失。数据保险箱支持通过控制台、API 等多样化方式快速简单接入,实现海量数据的存储管理。您可以使用数据保险箱对文件数据进行上传、下载,最终实现数据的安全存储和提取。
领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档