【caffe源码研究】第三章:源码篇(12) :激活函数层
2017-01-06 01:26
405 查看
以ReLULayer为例,比较简单,直接上代码
前向就是根据激活函数表达式计算,反向就是计算倒数。
前向就是根据激活函数表达式计算,反向就是计算倒数。
#include <algorithm> #include <vector> #include "caffe/layers/relu_layer.hpp" namespace caffe { template <typename Dtype> void ReLULayer<Dtype>::Forward_cpu(const vector<Blob<Dtype>*>& bottom, const vector<Blob<Dtype>*>& top) { const Dtype* bottom_data = bottom[0]->cpu_data(); Dtype* top_data = top[0]->mutable_cpu_data(); const int count = bottom[0]->count(); //negative_slope [默认值 0] : 当输入为x负数时,指定输出为negative_slope * x;默认值为0. //当输入为x正数时,指定输出为x; Dtype negative_slope = this->layer_param_.relu_param().negative_slope(); for (int i = 0; i < count; ++i) { top_data[i] = std::max(bottom_data[i], Dtype(0)) + negative_slope * std::min(bottom_data[i], Dtype(0)); } } } */ template <typename Dtype> void ReLULayer<Dtype>::Backward_cpu(const vector<Blob<Dtype>*>& top, const vector<bool>& propagate_down, const vector<Blob<Dtype>*>& bottom) { if (propagate_down[0]) { const Dtype* bottom_data = bottom[0]->cpu_data(); const Dtype* top_diff = top[0]->cpu_diff(); Dtype* bottom_diff = bottom[0]->mutable_cpu_diff(); const int count = bottom[0]->count(); Dtype negative_slope = this->layer_param_.relu_param().negative_slope(); for (int i = 0; i < count; ++i) { //当输入bottom_data大于0,则bottom_diff[i] = top_diff[i] //当输入bottom_data小于等于0,则bottom_diff[i] = top_diff[i] * negative_slope bottom_diff[i] = top_diff[i] * ((bottom_data[i] > 0) + negative_slope * (bottom_data[i] <= 0)); } } } #ifdef CPU_ONLY STUB_GPU(ReLULayer); #endif INSTANTIATE_CLASS(ReLULayer); } // namespace caffe
相关文章推荐
- 【caffe源码研究】第三章:源码篇(4) :Solver
- 【caffe源码研究】第三章:源码篇(9) :DataLayer
- 【caffe源码研究】第三章:源码篇(5) :Net
- 【caffe源码研究】第三章:源码篇(7) :Layer种类
- 【caffe源码研究】第三章:源码篇(11) :PoolingLayer
- 【caffe源码研究】第三章:源码篇(2) :Blob 和 SyncedMemory
- 【caffe源码研究】第三章:源码篇(8) :Layer代码
- 【caffe源码研究】第三章:源码篇(13) :损失层
- 【caffe源码研究】第三章:源码篇(6) :caffe.proto
- 【caffe源码研究】第三章:源码篇(1) :caffe整体架构
- 【caffe源码研究】第三章:源码篇(3) :工厂模式
- 【caffe源码研究】第三章:源码篇(10) :ConvolutionLayer
- 【caffe源码研究】第四章:完整案例源码篇(2) :LeNet初始化训练网络
- 【caffe源码研究】第四章:完整案例源码篇(1) :LeNetSolver初始化
- 【caffe源码研究】第四章:完整案例源码篇(5) :LeNet反向过程
- 【caffe源码研究】第四章:完整案例源码篇(3) :LeNet初始化测试网络
- 【caffe源码研究】第四章:完整案例源码篇(4) :LeNet前向过程
- 零基础学caffe源码 ReLU激活函数
- caffe中对6种激活函数类的封装--Absval
- caffe之(三)激活函数层