Caffe代碼導(dǎo)讀(2):caffe結(jié)構(gòu)分析

caffe目錄結(jié)構(gòu)

  • docs —— 幫助文檔
  • examples —— 代碼樣例
  • matlab —— MATLAB接口文件
  • python —— PYTHON接口文件
  • models —— 一些配置好的模型參數(shù)
  • scripts —— 一些文檔和數(shù)據(jù)會(huì)用到的腳本
  • 核心代碼:
    • tools —— 保存的源碼是用于生成二進(jìn)制處理程序的,caffe在訓(xùn)練時(shí)實(shí)際是直接調(diào)用這些二進(jìn)制文件
    • include —— Caffe的實(shí)現(xiàn)代碼的頭文件
    • src —— 實(shí)現(xiàn)Caffe的源文
    • gtest —— google test一個(gè)用于測(cè)試的庫. 你make runtest時(shí)看見的很多綠色RUN OK就是它,這個(gè)與caffe的學(xué)習(xí)無關(guān),不過是個(gè)有用的庫
    • caffe —— 關(guān)鍵代碼:
      • test —— 用gtest測(cè)試caffe的代碼
      • util —— 數(shù)據(jù)轉(zhuǎn)換時(shí)用的一些代碼。caffe速度快,很大程度得益于內(nèi)存設(shè)計(jì)上的優(yōu)化(blob數(shù)據(jù)結(jié)構(gòu)采用proto)和對(duì)卷積的優(yōu)化(部分與im2col相關(guān))
      • proto —— 即所謂的“Protobuf”,全稱“Google Protocol Buffer”,是一種數(shù)據(jù)存儲(chǔ)格式,幫助caffe提速
      • layers —— 深度神經(jīng)網(wǎng)絡(luò)中的基本結(jié)構(gòu)就是一層層互不相同的網(wǎng)絡(luò)了,這個(gè)文件夾下的源文件以及目前位置“src/caffe”中包含所有.cpp文件就是caffe的核心目錄下的核心代碼了。
  • caffe最核心的代碼:
    • blob[.cpp .h] —— 基本的數(shù)據(jù)結(jié)構(gòu)Blob類
    • common[.cpp .h] —— 定義Caffe類
    • internal_thread[.cpp .h]—— 使用boost::thread線程庫
    • net[.cpp .h] —— 網(wǎng)絡(luò)結(jié)構(gòu)類Net
    • solver[.cpp .h] —— 優(yōu)化方法類Solver
    • data_transformer[.cpp .h] —— 輸入數(shù)據(jù)的基本操作類DataTransformer
    • syncedmem[.cpp .h] —— 分配內(nèi)存和釋放內(nèi)存類CaffeMallocHost,用于同步GPU,CPU數(shù)據(jù)
    • layer[.cpp .h] —— 層類Layer
    • layers ——  此文件夾下面的代碼全部至少繼承了類Layer, 從layer_factory中注冊(cè)繼承

caffe的三級(jí)機(jī)構(gòu)(Blobs,Layers,Nets)

  • Blobs,Layers,Nets關(guān)系概述:Caff的net比作一棟大樓,Layer是構(gòu)成大樓的墻,Blob是構(gòu)成墻的磚塊

  • 功能概括:

    • Blob:用于數(shù)據(jù)的保存、交換和操作,Caffe基礎(chǔ)存儲(chǔ)結(jié)構(gòu)
    • Layer:用于模型和計(jì)算的基礎(chǔ)
    • Net:整合連接layers
  • 具體介紹:

    • Blob:是caffe中處理和傳遞實(shí)際數(shù)據(jù)的數(shù)據(jù)封裝包。是按C風(fēng)格連續(xù)儲(chǔ)存的N維數(shù)組。
      • 常規(guī)的維度為圖像數(shù)量N通道數(shù)C圖像高度H*圖像寬度W。

      • 主要變量:

        • shared_ptr data_;
        • shared_ptr diff_;
        • shared_ptr shape_data_;
        • vector shape_;
        • int count_;
        • int capacity_;
      • 解釋:

        • shared_ptr——是一個(gè)數(shù)據(jù)boost庫中的智能指針,主要用來申請(qǐng)內(nèi)存
        • data_主要是正向傳播時(shí)候用的,diff_主要是用來儲(chǔ)存偏差(主要是反向傳播的時(shí)候會(huì)用到),
        • shape_data和shape_——都是存儲(chǔ)Blob的形狀
        • count——表示Blob存儲(chǔ)的元素個(gè)數(shù),也就是個(gè)數(shù)*通道數(shù)*高度*寬度
        • capacity_——表示當(dāng)前Blob的元素個(gè)數(shù)(控制動(dòng)態(tài)分配)
      • 主要函數(shù):

        • 構(gòu)造函數(shù):構(gòu)造函數(shù)開辟一個(gè)內(nèi)存空間來存儲(chǔ)數(shù)據(jù)
        • reshape函數(shù):Reshape函數(shù)在Layer中的reshape或者forward操作中來adjust dimension
        • count函數(shù):重載很多個(gè)count()函數(shù),主要還是為了統(tǒng)計(jì)Blob的容量(volume),或者是某一片(slice),從某個(gè)axis到具體某個(gè)axis的shape乘積(如 “ inline int count(int start_axis, int end_axis)”)。
        • data_數(shù)據(jù)操作函數(shù) & 反向傳播導(dǎo)數(shù)diff_操作函數(shù):這一部分函數(shù)主要通過給定的位置訪問數(shù)據(jù),根據(jù)位置計(jì)算與數(shù)據(jù)起始的偏差offset,在通過cpu_data*指針獲得地址
        • FromProto/ToProto數(shù)據(jù)序列化:將數(shù)據(jù)序列化,存儲(chǔ)到BlobProto,這里說到Proto是谷歌的一個(gè)數(shù)據(jù)序列化的存儲(chǔ)格式,可以實(shí)現(xiàn)語言、平臺(tái)無關(guān)、可擴(kuò)展的序列化結(jié)構(gòu)數(shù)據(jù)格式。
        • Update函數(shù):該函數(shù)用于參數(shù)blob的更新(weight,bias 等減去對(duì)應(yīng)的導(dǎo)數(shù))
        • 其他運(yùn)算函數(shù):
          • Dtype asum_data() const;//計(jì)算data的L1范數(shù)(所有元素絕對(duì)值之和)
          • Dtype asum_diff() const;//計(jì)算diff的L1范數(shù)
          • Dtype sumsq_data() const;//計(jì)算data的L2范數(shù)(所有元素平方和)
          • Dtype sumsq_diff() const;//計(jì)算diff的L2范數(shù)
          • void scale_data(Dtype scale_factor);//將data部分乘以一個(gè)因子
          • void scale_diff(Dtype scale_factor);//將diff部分乘一個(gè)因子
    • layer:
      • 簡(jiǎn)介:
        所有的Pooling(池化),Convolve(卷積),apply nonlinearities等操作都在這里實(shí)現(xiàn)。在Layer中input data用bottom,表示output data用top表示。每一層定義了三種操作setup(Layer初始化), forward(正向傳導(dǎo),根據(jù)input計(jì)算output), backward(反向傳導(dǎo)計(jì)算,根據(jù)output計(jì)算input的梯度)。forward和backward有GPU和CPU兩個(gè)版本的實(shí)現(xiàn)。

      • caffe中已經(jīng)衍生了很多不同功能作用的layer, 其中常用的五種layer:

        • data_layer(數(shù)據(jù)層)
          • data_layer主要包含與數(shù)據(jù)有關(guān)的文件。在官方文檔中指出data是caffe數(shù)據(jù)的入口是網(wǎng)絡(luò)的最低層,并且支持多種格式,在這之中又有5種LayerType:

            • DATA 用于LevelDB或LMDB數(shù)據(jù)格式的輸入的類型,輸入?yún)?shù)有source, batch_size, (rand_skip), (backend)。后兩個(gè)是可選。
            • EMORY_DATA 這種類型可以直接從內(nèi)存讀取數(shù)據(jù)使用時(shí)需要調(diào)用MemoryDataLayer::Reset,輸入?yún)?shù)有batch_size, channels, height, width。
            • DF5_DATA HDF5數(shù)據(jù)格式輸入的類型,輸入?yún)?shù)有source, batch_size。
            • HDF5_OUTPUT HDF5數(shù)據(jù)格式輸出的類型,輸入?yún)?shù)有file_name。
            • IMAGE_DATA 圖像格式數(shù)據(jù)輸入的類型,輸入?yún)?shù)有source, batch_size, (rand_skip), (shuffle), (new_height), (new_width)。
          • 其實(shí)還有兩種WINDOW_DATA, DUMMY_DATA用于測(cè)試和預(yù)留的接口,不重要。

        • neuron_layer(數(shù)據(jù)的操作層)
          neuron_layer實(shí)現(xiàn)里大量激活函數(shù),主要是元素級(jí)別的操作,具有相同的bottom,top size。
        • loss_layer(損失層/計(jì)算網(wǎng)絡(luò)誤差層)

        可以看見調(diào)用了neuron_layers.hpp,估計(jì)是需要調(diào)用里面的函數(shù)計(jì)算Loss,一般來說Loss放在最后一層。caffe實(shí)現(xiàn)了大量loss function,它們的父類都是LossLayer。

        • common_layer

          • 這一層主要進(jìn)行的是vision_layer的連接
          • 聲明了9個(gè)類型的common_layer,部分有GPU實(shí)現(xiàn):
            • InnerProductLayer 常常用來作為全連接層
            • SplitLayer 用于一輸入對(duì)多輸出的場(chǎng)合(對(duì)blob)
            • FlattenLayer 將n * c * h * w變成向量的格式n * ( c * h * w ) * 1 * 1
            • ConcatLayer 用于多輸入一輸出的場(chǎng)合
            • SilenceLayer 用于一輸入對(duì)多輸出的場(chǎng)合(對(duì)layer)
            • (Elementwise Operations) 這里面是我們常說的激活函數(shù)層Activation Layers。
              • EltwiseLayer
              • SoftmaxLayer
              • ArgMaxLayer
              • MVNLayer
        • vision_layer

          • 主要是實(shí)現(xiàn)Convolution和Pooling操作, 主要有以下幾個(gè)類:
            • ConvolutionLayer 最常用的卷積操作
            • Im2colLayer 與MATLAB里面的im2col類似,即image-to-column transformation,轉(zhuǎn)換后方便卷積計(jì)算
            • LRNLayer 全稱local response normalization layer,在Hinton論文中有詳細(xì)介紹ImageNet.
              Classification with Deep Convolutional Neural Networks 。
            • PoolingLayer Pooling操作
    • Net

    Net由一系列的Layer組成(無回路有向圖DAG),Layer之間的連接由一個(gè)文本文件描述。模型初始化Net::Init()會(huì)產(chǎn)生blob和layer并調(diào)用Layer::SetUp。在此過程中Net會(huì)報(bào)告初始化進(jìn)程。這里的初始化與設(shè)備無關(guān),在初始化之后通過Caffe::set_mode()設(shè)置Caffe::mode()來選擇運(yùn)行平臺(tái)CPU或GPU,結(jié)果是相同的。

    • Protocol Buffer

      • Protocol Buffer(PB)是一種輕便、高效的結(jié)構(gòu)化數(shù)據(jù)存儲(chǔ)格式,可以用于結(jié)構(gòu)化數(shù)據(jù)串行化,很適合做數(shù)據(jù)存儲(chǔ)或 RPC 數(shù)據(jù)交換格式。它可用于通訊協(xié)議、數(shù)據(jù)存儲(chǔ)等領(lǐng)域的語言無關(guān)、平臺(tái)無關(guān)、可擴(kuò)展的序列化結(jié)構(gòu)數(shù)據(jù)格式。是一種效率和兼容性都很優(yōu)秀的二進(jìn)制數(shù)據(jù)傳輸格式,目前提供了 C++、Java、Python 三種語言的 API。Caffe采用的是C++和Python的API。
最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請(qǐng)聯(lián)系作者
【社區(qū)內(nèi)容提示】社區(qū)部分內(nèi)容疑似由AI輔助生成,瀏覽時(shí)請(qǐng)結(jié)合常識(shí)與多方信息審慎甄別。
平臺(tái)聲明:文章內(nèi)容(如有圖片或視頻亦包括在內(nèi))由作者上傳并發(fā)布,文章內(nèi)容僅代表作者本人觀點(diǎn),簡(jiǎn)書系信息發(fā)布平臺(tái),僅提供信息存儲(chǔ)服務(wù)。

相關(guān)閱讀更多精彩內(nèi)容

友情鏈接更多精彩內(nèi)容