用传统梯度下降法驯服误差曲面:算法简介和示例
2023-09-25 04:45:55
在机器学习的迷人世界中,梯度下降法犹如一位忠诚的向导,引领着我们穿梭于误差曲面的起伏跌宕,最终找到最优解。在这趟算法之旅中,我们将探寻传统梯度下降法的奥秘,以一元二次函数、非凸函数和二元函数为练兵场,揭开算法的特性和应用秘籍。
算法原理:逐小步迈向最优
传统梯度下降法基于这样一个直观的思想:沿着误差曲面的负梯度方向,小步小步地更新参数,直到误差最小化。它的数学公式简洁而优雅:
θ = θ - α * ∇f(θ)
其中,θ是模型参数,α是学习率,∇f(θ)是误差函数f(θ)的梯度。
代码实现:一元二次函数初探
让我们从最简单的案例入手——一元二次函数。其误差函数为f(x) = (x - 2)^2,梯度为f'(x) = 2(x - 2)。根据梯度下降公式,我们写出Python代码:
import numpy as np
def gradient_descent(x0, alpha, num_iter):
x = x0
for i in range(num_iter):
grad = 2 * (x - 2)
x = x - alpha * grad
return x
x0 = 5 # 初始值
alpha = 0.1 # 学习率
num_iter = 100 # 迭代次数
result = gradient_descent(x0, alpha, num_iter)
print(f"最优解:{result:.4f}")
运行代码后,我们会发现算法成功找到了最优解x = 2。
非凸函数:崎岖地形的挑战
非凸函数的误差曲面布满峰谷,对传统梯度下降法提出了严峻挑战。考虑函数f(x) = x^4 - 2x^2 + 1。其梯度为f'(x) = 4x^3 - 4x,在区间[-2, 2]内有多个极值点。
针对这种场景,我们优化了代码:
import numpy as np
from scipy.optimize import minimize
def gradient_descent(x0, alpha, num_iter):
result = minimize(lambda x: (x - 2)**4 - 2*(x - 2)** 2 + 1, x0, method='BFGS', options={'maxiter': num_iter})
return result.x
x0 = 5 # 初始值
alpha = 0.1 # 学习率
num_iter = 100 # 迭代次数
result = gradient_descent(x0, alpha, num_iter)
print(f"最优解:{result:.4f}")
通过使用BFGS算法作为优化器,我们可以克服非凸函数的挑战,找到全局最优解。
二元函数:多维空间的探索
二元函数的误差曲面更加复杂多变。考虑函数f(x, y) = (x - 2)^2 + (y - 3)^2。其梯度为∇f(x, y) = [2(x - 2), 2(y - 3)]。
import numpy as np
from scipy.optimize import minimize
def gradient_descent(x0, y0, alpha, num_iter):
result = minimize(lambda params: (params[0] - 2)**2 + (params[1] - 3)** 2, x0=np.array([x0, y0]), method='BFGS', options={'maxiter': num_iter})
return result.x
x0 = 5 # 初始值
y0 = 4 # 初始值
alpha = 0.1 # 学习率
num_iter = 100 # 迭代次数
result = gradient_descent(x0, y0, alpha, num_iter)
print(f"最优解:{result}")
运行代码后,算法成功找到了最优解[2, 3]。
算法依赖性:步履轻盈还是沉重
初始值的影响
传统梯度下降法对初始值的选择十分敏感。不同的初始值可能导致算法收敛到不同的极值点。为了避免陷入局部最优解,通常采用多组不同的初始值进行多次优化,取其中最优的结果。
学习率的选择
学习率α控制着算法的步长。太小,算法收敛缓慢;太大,算法可能不稳定,甚至导致发散。选择合适的学习率至关重要。可以通过试错法或者自适应学习率策略来确定最优的α值。
代码优化:提升速度和效率
针对大规模数据或复杂模型,优化代码可以显著提升梯度下降法的运行效率。一些常见的优化技巧包括:
- 向量化代码:使用NumPy等库进行向量化运算,提高并行化程度。
- 批处理:将数据分批处理,降低单次迭代的计算量。
- 提前计算:对不变的梯度项进行预计算,减少重复计算。
结语
传统梯度下降法是一种强大的优化算法,它能高效地解决各种机器学习问题。通过深入理解算法原理、细致调参和代码优化,我们可以充分发挥其优势,征服误差曲面的险峰,找到问题的最优解。