在caffe框架中新增新增乙個簡單的新層

2021-08-17 14:46:35 字數 4228 閱讀 7504

沒錯,我又來水經驗了。在深度學習網路框架caffe中新增乙個簡單的新層,用來實現原框架中所沒有的功能:輸出一句話,以及乙個看起來似乎並沒有什麼實際作用的引數,下面詳細展開來說。

1.  首先,本文實現的layer名稱為allpasslayer,這裡不能和已有的層同名,功能為將輸入到該層的資料不做任何改變直接輸出到下一層(其間輸出一句話和乙個引數,證明資料確實經過了這個層)。allpasslayer層的forward和backwark實現非常容易,直接將輸入的blob資料複製到輸出的blob中,因此基本可以加入到任何已有網路中,不影響訓練和測試的結果。

2.  新增新的層aallpasslayer的實現,需要同其他的layer類一樣,分成宣告和實現兩個部分,對應放在.hpp和.cpp檔案中,如果用到gpu的話,還應該有相應的.cu檔案。其中.hpp標頭檔案放在/caffe-windows/include/caffe/layers/資料夾下,而 .cpp 和 .cu 放入/caffe-windows/src/caffe/layers下。這裡僅實現cpu上的**。 

all_pass_layer.hpp

#ifndef caffe_all_pass_layer_hpp_  

#define caffe_all_pass_layer_hpp_

#include #include "caffe/blob.hpp"

#include "caffe/layer.hpp"

#include "caffe/proto/caffe.pb.h"

#include "caffe/layers/neuron_layer.hpp"

namespace caffe

virtual inline const char* type() const

protected:

virtual void forward_cpu(const vector*>& bottom,

const vector*>& top);

virtual void forward_gpu(const vector*>& bottom,

const vector*>& top);

virtual void backward_cpu(const vector*>& top,

const vector& propagate_down, const vector*>& bottom);

virtual void backward_gpu(const vector*>& top,

const vector& propagate_down, const vector*>& bottom);

};} // namespace caffe

#endif // caffe_all_pass_layer_hpp_

正如所看到的那樣,上面只是一些函式的宣告,並沒有具體的實現,實現的話要寫在.cpp檔案中。

all_pass_layer.cpp

#include #include #include "caffe/layers/all_pass_layer.hpp"  

#include using namespace std;

#define debug_ap(str) cout& bottom,

const vector*>& top)

caffe_copy(count, bottom_data, top_data);

//注意:獲取引數的兩個變數 "all_pass_param" 和 "key"

debug_ap("here is all pass layer, forwarding.");

debug_ap(this->layer_param_.all_pass_param().key());

}template void allpasslayer::backward_cpu(const vector*>& top,

const vector& propagate_down,

const vector*>& bottom)

caffe_copy(count, top_diff, bottom_diff);

}//同上

debug_ap("here is all pass layer, backwarding.");

debug_ap(this->layer_param_.all_pass_param().key());

}#ifdef cpu_only

stub_gpu(allpasslayer);

#endif

//注意:下面2行對層進行註冊,必不可少;注意巨集引數不能弄錯

instantiate_class(allpasslayer); // 類的名稱 allpasslayer

register_layer_class(allpass); // 層的名稱 allpass

} // namespace caffe

3.修改caffe.proto檔案

由於我們新新增的層是帶有引數的,因此需要在caffe.proto中進行相應的註冊和修改。

首先開啟caffe/src/caffe/proto/

caffe.proto檔案,找到message layerparameter{},在這裡我們要為新新增的層註冊乙個類似於id的東西。

順便更改一下這個:

我們需要為新新增的層創造乙個message函式:

message allpassparameter
另外還要找到message v1layerparameter裡enum layertype處加入id,如下圖:

在message v1layerparameter的最後加入id:

如果新增的層引數用到之前沒有定義的引數變數,我們還要在message v0layerparameter{}加入定義,我們定義的有乙個引數key,因此需要在v0layerparameter中新增如下:

4.  另外還有乙個要修改的在~\caffe-master\src\caffe\util\內upgrade_proto.cpp裡const char* upgradev1layertype(const v1layerparameter_layertype type) {

這裡allpass與v1layerparameter內的type名稱要保持一致。

5. 最後一步,對於windows下來說,也是最重要的一部,找到caffe/windows/libcaffe/下的libcaffe.vcxproj和libcaffe.vcxproj.filters進行修改,加入.hpp,.cpp,.cu(如果有的話)檔案的路徑:

第一步,在libcaffe.vcxproj加入

第二步:在libcaffe.vcxproj.filters加入

最後再重新編譯caffe就可以了

以測試mnist為例,我將成功加入的層新增在了data層和第一層卷積層之間:

下面是用一張手寫體數字進行測試的結果:

可以看到成功輸出了一句話和乙個引數,說明新增新層成功了。^_^

在新版caffe中新增center loss層

準備工作 1,首先你需要有乙個可以make編譯通過的caffe 這個過程在第一篇blog中已經寫出 和乙個帶有center loss層的caffe face 可以直接在github上clone下來 caffe face git clone git新增原因 1,在分類問題上,center loss可以...

在 DataGridView中新增乙個統計行的技巧

dim mtalbe as new datatable mtalbe mbl.getlist pstrsql tables 0 dim dr as datarow mtalbe.newrow dr.item 0 mtalbe.rows.count dr.item 9 mtalbe.compute s...

在caffe中新增新的Layer

參考github上面的答案 here s roughly the process i follow.大致過程翻譯 然後在對應的hpp標頭檔案中新增該層的類的定義。包括內聯實現type和 blob 方法指定blob的數字,如果你只是實現cpu部分的 則忽略 gpu的宣告 2.實現你要新增的層 應該指的...