caffe中的softmax layer
2016-05-25 11:01
399 查看
在caffe中的lenet实现最后一层是softmax layer,输出分类的结果,下面就简单介绍一下softmax回归。
1,首先,在caffe中,softmax layer输出的是原始的输入在每一个分类标签上的概率,例如在lenet网络中,输出的分类共有0-9的10中分类,那么softmax layer就会输出含有10个元素的向量,每一个元素表示输入在每一个分类上的概率。
那么,用softmax的目的是让输入在正确的分来标签上的概率最大,这就是我们优化的目标函数,普通的优化函数只是比较输出和标签的差值,然后对差值进行优化,让其最小,就可以得出网络的参数值。但是在分类中,这种方法不太适用,因为输出的结果不是连续的,而是离散的,是无法对其求梯度的,所以要从概率的角度进行考虑。
那么问题来了,从概率的角度进行优化是可行的,但是输入在每个标签上的概率应该怎么求呢,这是一个多元分布问题,而softmax就是解决多元分布问题的,在介绍具体的过程之前,我们先看softmax layer的输入代表的含义,在《deeping learning》的181页有这么一句话:we can think of a as a vector of scores whose elements a(i) as associated with each category i, with larger relative
scores yielding exponentially larger probabilities. 就是说softmax layer的输入可以看作是输入在每个标签上的打分,分数越高,说明输入越有可能属于这个标签上,那么我们也可以利用这个分数求输入相对于每个标签的概率,分数越高,概率越大。
2, softmax回归
网上有很多关于softmax回归的帖子,我的理解是softmax本质的作用就是计算softmax layer的输入在每一个标签上的概率,caffe中softmax_layer的过程如下:
(1)找出输入的最大值;
(2)输入的每一个变量都减去最大值;
(3)对(2)中结果求去指数函数;
(4)对(3)中结果归一化,得出的结果就是输入在每一个标签上概率。
caffe中代码是在softmax_layer.cpp Line 37
下面最重要的是求去代价函数,代价函数本质上就是输入在对应的正确的标签上的概率,我们优化的目标就是使这个概率最大,一般我们都是对概率取个log运算,然后,由于网络的训练是以batch为单位的,假如一个batch里有100个样本,我们就要对这100个样本的log(概率)进行求和,然后平均,最后我们就是利用这个代价函数求梯度,然后利用梯度更新权值。caffe中代码是在softmax_loss_layer.cpp中Line 100
关于softmax的具体原理,参考下面两个博客:
(1)http://ufldl.stanford.edu/wiki/index.php/Softmax%E5%9B%9E%E5%BD%92
(2)http://blog.csdn.net/acdreamers/article/details/44663305
1,首先,在caffe中,softmax layer输出的是原始的输入在每一个分类标签上的概率,例如在lenet网络中,输出的分类共有0-9的10中分类,那么softmax layer就会输出含有10个元素的向量,每一个元素表示输入在每一个分类上的概率。
那么,用softmax的目的是让输入在正确的分来标签上的概率最大,这就是我们优化的目标函数,普通的优化函数只是比较输出和标签的差值,然后对差值进行优化,让其最小,就可以得出网络的参数值。但是在分类中,这种方法不太适用,因为输出的结果不是连续的,而是离散的,是无法对其求梯度的,所以要从概率的角度进行考虑。
那么问题来了,从概率的角度进行优化是可行的,但是输入在每个标签上的概率应该怎么求呢,这是一个多元分布问题,而softmax就是解决多元分布问题的,在介绍具体的过程之前,我们先看softmax layer的输入代表的含义,在《deeping learning》的181页有这么一句话:we can think of a as a vector of scores whose elements a(i) as associated with each category i, with larger relative
scores yielding exponentially larger probabilities. 就是说softmax layer的输入可以看作是输入在每个标签上的打分,分数越高,说明输入越有可能属于这个标签上,那么我们也可以利用这个分数求输入相对于每个标签的概率,分数越高,概率越大。
2, softmax回归
网上有很多关于softmax回归的帖子,我的理解是softmax本质的作用就是计算softmax layer的输入在每一个标签上的概率,caffe中softmax_layer的过程如下:
(1)找出输入的最大值;
(2)输入的每一个变量都减去最大值;
(3)对(2)中结果求去指数函数;
(4)对(3)中结果归一化,得出的结果就是输入在每一个标签上概率。
caffe中代码是在softmax_layer.cpp Line 37
for (int i = 0; i < outer_num_; ++i) { // use softmax to calculate the hypothesis function // initialize scale_data to the first plane caffe_copy(inner_num_, bottom_data + i * dim, scale_data); for (int j = 0; j < channels; j++) { for (int k = 0; k < inner_num_; k++) { scale_data[k] = std::max(scale_data[k], bottom_data[i * dim + j * inner_num_ + k]); } } // subtraction caffe_cpu_gemm<Dtype>(CblasNoTrans, CblasNoTrans, channels, inner_num_, 1, -1., sum_multiplier_.cpu_data(), scale_data, 1., top_data); // exponentiation caffe_exp<Dtype>(dim, top_data, top_data); // sum after exp caffe_cpu_gemv<Dtype>(CblasTrans, channels, inner_num_, 1., top_data, sum_multiplier_.cpu_data(), 0., scale_data); // division for (int j = 0; j < channels; j++) { caffe_div(inner_num_, top_data, scale_data, top_data); top_data += inner_num_; } }
下面最重要的是求去代价函数,代价函数本质上就是输入在对应的正确的标签上的概率,我们优化的目标就是使这个概率最大,一般我们都是对概率取个log运算,然后,由于网络的训练是以batch为单位的,假如一个batch里有100个样本,我们就要对这100个样本的log(概率)进行求和,然后平均,最后我们就是利用这个代价函数求梯度,然后利用梯度更新权值。caffe中代码是在softmax_loss_layer.cpp中Line 100
for (int i = 0; i < outer_num_; ++i){ // sample by sample for (int j = 0; j < inner_num_; j++) { const int label_value = static_cast<int>(label[i * inner_num_ + j]); if (has_ignore_label_ && label_value == ignore_label_) { continue; } DCHECK_GE(label_value, 0); DCHECK_LT(label_value, prob_.shape(softmax_axis_)); loss -= log(std::max(prob_data[i * dim + label_value * inner_num_ + j], Dtype(FLT_MIN))); // cost function ++count; } } top[0]->mutable_cpu_data()[0] = loss / get_normalizer(normalization_, count);
关于softmax的具体原理,参考下面两个博客:
(1)http://ufldl.stanford.edu/wiki/index.php/Softmax%E5%9B%9E%E5%BD%92
(2)http://blog.csdn.net/acdreamers/article/details/44663305
相关文章推荐
- 非常好的解释AngularJs中Factory和Service和Provide不同
- 挂载fedora安装光盘小系统squashfs.img命令
- webstorm-前端javascript开发神器中文教程和技巧分享
- HTMl5的sessionStorage和localStorage
- webstorm-前端javascript开发神器中文教程和技巧分享(转)
- HTML学习笔记(1) - HTML简介
- 前端页面缓存心得体会
- JavaScript笔记
- 基于 JQUERY 网页 banner
- html5带下拉框的input
- h5-news_index
- 判断JS对象是否具有某种属性
- jQuery获取复选框被选中数量及判断选择值的方法详解
- js提交form表单,并传递参数的实现方法
- 剑指offer26 复杂链表的复制
- jQuery中的data方法只能获取不能设置值?
- Annotation注解与butterknife
- JavaScript输入输出
- 剑指offer16--二叉树的镜像处理
- js数组对象--数据格式的转换(字符串,对象的取值与赋值)