1.向量化: 在上一节中,我们推导出求解梯度的公式如下: 继续变形,使其可以向量化,如下: 于是求梯度的函数的实现方式也相应的改变,如下:
def dJ(theta, X_b, y): # res = np.empty(len(theta)) # res[0] = np.sum(X_b.dot(theta) - y) # for i in range(1, len(theta)): # res[i] = (X_b.dot(theta) - y).dot(X_b[:,i]) # return res * 2 / len(X_b) return X_b.T.dot(X_b.dot(theta) - y) * 2. / len(X_b)下面将梯度下降法并且向量化之后的线性回归模型用在真实数据中: (1).准备数据,依然为波士顿房价: (2).使用梯度下降法: 会发现此时会报错,并且参数coef_中都是nan。为什么会overflow呢?原因在于对于真实的数据集,如下: 每一个特征所对应的数据规模是不一样的,面对这样一个数据,我们实际求得的梯度很有可能结果也是非常大的。我们使用默认的eta,最终形成的步长还是太大,使得我们梯度下降法的过程是不收敛的。
为了解决以上的问题,我们可以减小学习率eta的值,但是如果eta太小,导致每一步行进的都非常小,那我们需要用更多的循环次数来找到损失函数的最小值。以下为验证这个结论的过程: 2.数据归一化: 以上可以看到,减小了学习率eta的值,使得循环次数增大,甚至需要更大,这样就会很耗时。为了解决这个问题,我们需要对数据进行归一化处理。 使用梯度下降前进行数据归一化: 所以,当我们使用梯度下降法搜索损失函数的最小值之前,对数据需要进行归一化处理。
3.使用梯度下降法的优势: 当矩阵比较大时,由于正规方程法是对矩阵进行运算,相应的会比较耗时;使用梯度下降法就会提高效率: