如今深度学习如火如荼,各种工具和平台都已经非常完善。各大训练平台比如 TensorFlow 让我们可以更多的聚焦在网络定义部分,而不需要纠结求导和 Layer 的内部组成。本系列我们来回顾一下深度学习的各个基础环节,包括线性回归,BP 算法的推导,卷积核和 Pooling,循环神经网络,LSTM 的 Memory Block 组成等,全文五篇,前三篇是斯坦福深度学习 wiki 整理,第四第五两篇是 Alex Graves 的论文读书笔记,图片来自网络和论文,有版权问题请联系我们。
假如一个 target label 是与各种要素Xi呈线性关系的,我们可以用线性回归来拟合,,认为。
为了达到数据拟合的目的,可以用最小二乘的方法来训练调整参数 ,也就是找到一组参数 ,使得最小化。
此问题的一类求解方法是通过梯度下降,每次对 进行求导,并不断沿梯度下降的方向更新,使得 不断减小并趋向于 0 。我们对公式中的每个 分别求偏导数,可以得到: 。
这个公式在编程的时候如何实现呢?首先我们把每一个 和 对应的数据叫做一个 instance ,一般是机器学习训练数据里面的一行。通过当前的向量,先求得 ,他一般是一个浮点数,直接与 相减得到偏导公式的后一部分,我们叫它为残差。然后直接对该 instance 中的每个位置的 (如果有值的话)乘上这个残差,得到对应元素位置的 的偏导数。
这样得到的偏导数也是一个向量,里面的元素与向量一一对应。我们选定一个叫学习率的参数 ,将这个偏导数向量更新到向量上,就完成了一次迭代: 。
重复上述过程,直到足够小,我们就得到了需要的参数。这样当我们拿到一组新的 ,但是不知道他对应的 是多少时,可以通过 计算得到一个近似的 ,也就是我们所说的预测过程。
上面讲的线性回归可以用来预测连续值,但是很多时候我们希望做的是一个分类问题,也就是预测一个 instance 属于某个分类(比如:是/否,A/B/C等)的概率。逻辑回归就是完成此类任务的一个比较简单的方案。
在之前的线性回归的基础上,如果要预测的 y 是一个离散值(简单起见,后面以来举例,多个离散值同样可以简化为若干个二值问题),我们增加一个叫 sigmoid 或者 logistic 的操作,把上面的连续值域映射到 [0, 1] ,我们认为他代表该 instance 对应这个 y 取值的概率:
与上面的线性回归类似,现在我们的目标是找到一组参数,使得每个 instance 预测出来的概率最大化,即 y=1 的时候 尽可能大,而 y=0 的时候 尽可能大。回想我们学过的概率论,对于这样的一组二项分布数据 我们的目标是似然概率最大化:
求 L 最大化的问题,同样可以通过求 -L 最小化来实现,与线性回归参数求解一样,同样通过梯度下降法来更新向量。在直接进行求导之前,先对 -L 取 log ,将连乘变为累加,方便求导:
一旦我们求得了一组合适的参数,就可以对新的不含 label ( y 值) 的 instance 进行预测,比如 ,我们可以认为要预测的 y 取值为 1 。
现在来看看通过梯度下降如何求借。通用需要对进行每一项求偏导,推导过程需要先对公式进行简化和合并:
所以对前一部分求偏导 ,对后一部分也求偏导
,代入上面的 可以得到:
更新方式与线性回归类似:
程序实现上,同样先是拿到 后计算,然后与进行按位乘操作,得到 的每个元素位,然后对进行按位的更新。
在程序开发的过程中,我们不可能对每个 instance 的每个位用 for 循环来操作,一般将和 x 当做一整个向量,用 blas 这样的科学计算库来进行加速。
对于多条 instance 的 x 可以当做一个矩阵,和 y 分别是两个一维向量,这样可以进一步使用 blas 的矩阵计算进行加速。
由于逻辑回归通常是对超高维的和 x 进行计算,在进行预测的时候 x 是非常稀疏的,只有少数元素不为 0 ,此时对于单条记录计算 反而是通过一个 index->weight 的 hashmap 查找对应位置的来计算更方便。
在进行开发的时候,有时候不确定我们的推导或者公式编码是否正确,这时候需要从数据上推断结果是否正确。有一个简单的办法是通过近似的导数来检查。
因此实际进行调试的时候,我们可以通过 算一个近似值,来跟我们编码后的梯度求导进行对比。一般取 时,求导公式得到的结果与上面的近似值会有至少 4 位有效数字是一致的。
上面是对一维变量进行求导。如果是逻辑回归这样的参数,通常是一个向量,我们如何检查呢?有一个办法是对每一维独立检查,比如有 N 维,我们从 0 到 N-1 ,分别只对这一维单独加减 EPSILON ,其他元素保持不变。然后应用上面的方法,来独立检查这一维的求导结果是否正确。
上面介绍的逻辑回归是一个二值化问题,y 的取值只有 0 和 1 ,如果我们的预测任务 ,那么我们需要 softmax regression 来进行建模和预测。简单一些理解,可以认为 softmax regression 是 K 个 logistic regression 的归一化:
需要注意的是, 本身就是一个向量,类似逻辑回归里面的 ,因为 x 作为输入对于所有的 K 个分类都是一样的,所以每个分类都有一个属于自己的 向量,所有的 K 个 一起叫做 softmax regression 的模型,该模型的概率表达是:
还是按照前面的套路,我们需要定义一个代价函数来定义模型对数据拟合的代价,并且通过最优化方法使得代价最小化。首先定义指示函数:
通过对所有 instance 拟合的概率最大化,有:
同样取负数把优化目标变为最小化,然后取 log ,得到代价函数:
下面的求导,为了推导方便,我们直接对 进行求导,实际操作的时候是对向量元素的操作。先单独对求和部分里面的 进行求导:
上式是对所有的 k 无差别化的求偏导,结合前面的系数 进行展开, 展开后只剩下 ,后面部分实际上就是 ,因此:
在编程实现的时候, 是一个向量,因此仍然需要按位操作求导和更新。同时,我们发现每一个 instance 实际上都要对 1,2,…,K 的所有进行梯度计算和更新,当 的时候 , 前面多了一项 ,而对于其他的 仍然是能计算梯度值的,因为实际中即使当 时模型仍然是有概率值的,并不是 0 。
逻辑回归可以看做是 softmax regression 在 K=2 的时候的特殊情况,那么什么时候使用逻辑回归,什么时候使用 softmax regression 呢?举一个例子,对一篇讲金融和互联网结合的文章进行分类,如果你只允许每篇文章有一个分类值,选互联网就不能是金融,那么就用 softmax regression ,所有 K 个值是归一化的,每次只能输出一个概率最大值作为结果。如果允许给文章打上 <金融,互联网> 两个标签,则可以训练两个逻辑回归分类器,对金融和互联网的概率分别预测。
与逻辑回归的差别:上面我们提到 LR 和 softmax 都可以对 K=2 的任务进行回归预测,而且两种 label 的概率之和都是 1 ,看起来模型训练的时候,二分类问题用两种算法应该是没有区别的?其实不然,从上面的 softmax 求导过程可以发现 对预测结果等于 1 和等于 0 的两部分分别计算误差,更新梯度;而 LR 只利用一个误差来更新梯度。因此同样是二分类问题,softmax 的收敛速度比 LR 更快一些。
梯度下降法
此处可以延展开很多内容,比如随机梯度下降,牛顿法,L-BFGS 等。建议自己系统性的学习了解一下。