一、梯度下降:从基础到变种
梯度下降是机器学习中最基础的优化算法,它的核心思想是通过迭代调整参数,逐步逼近损失函数的最小值。想象一下你在山上蒙着眼睛找下山的路,每次只能试探周围一小步,选择最陡的方向迈出一步——这就是梯度下降的直观比喻。
1.1 标准梯度下降(Batch GD)
标准的梯度下降在每次迭代时使用全部训练数据计算梯度,虽然方向准确,但计算量大。例如,用Python实现线性回归的梯度下降:
# 技术栈:Python + NumPy
import numpy as np
def batch_gradient_descent(X, y, learning_rate=0.01, epochs=1000):
m, n = X.shape
theta = np.zeros(n) # 初始化参数
for _ in range(epochs):
gradient = (1/m) * X.T @ (X @ theta - y) # 计算梯度(全部数据)
theta -= learning_rate * gradient # 更新参数
return theta
1.2 随机梯度下降(SGD)
SGD每次随机选一个样本计算梯度,速度快但波动大。适合大规模数据:
def stochastic_gradient_descent(X, y, learning_rate=0.01, epochs=100):
m, n = X.shape
theta = np.zeros(n)
for _ in range(epochs):
for i in range(m):
random_idx = np.random.randint(m)
xi, yi = X[random_idx], y[random_idx]
gradient = xi * (xi @ theta - yi) # 单样本梯度
theta -= learning_rate * gradient
return theta
1.3 小批量梯度下降(Mini-batch GD)
折中方案:每次用一小批数据。例如批量大小为32:
def mini_batch_gradient_descent(X, y, batch_size=32, learning_rate=0.01, epochs=100):
m, n = X.shape
theta = np.zeros(n)
for _ in range(epochs):
indices = np.random.permutation(m)
X_shuffled, y_shuffled = X[indices], y[indices]
for i in range(0, m, batch_size):
X_batch = X_shuffled[i:i+batch_size]
y_batch = y_shuffled[i:i+batch_size]
gradient = (1/batch_size) * X_batch.T @ (X_batch @ theta - y_batch)
theta -= learning_rate * gradient
return theta
优缺点对比:
- Batch GD:稳定但慢,适合小数据。
- SGD:快但噪声大,需动态调整学习率。
- Mini-batch GD:平衡效率与稳定性,最常用。
二、反向传播:神经网络的引擎
反向传播是训练神经网络的核心算法,通过链式法则将误差从输出层反向传递到每一层。以简单的3层网络为例:
# 技术栈:Python + NumPy
class NeuralNetwork:
def __init__(self, input_size, hidden_size, output_size):
self.W1 = np.random.randn(input_size, hidden_size) * 0.01
self.W2 = np.random.randn(hidden_size, output_size) * 0.01
def forward(self, X):
self.z1 = X @ self.W1
self.a1 = np.tanh(self.z1) # 隐藏层激活函数
self.z2 = self.a1 @ self.W2
return self.z2 # 输出层(未激活)
def backward(self, X, y, learning_rate):
m = X.shape[0]
# 输出层误差
dz2 = (self.z2 - y) / m
dW2 = self.a1.T @ dz2
# 隐藏层误差
dz1 = (dz2 @ self.W2.T) * (1 - np.tanh(self.z1)**2) # tanh导数
dW1 = X.T @ dz1
# 更新权重
self.W1 -= learning_rate * dW1
self.W2 -= learning_rate * dW2
关键点:
- 前向传播计算预测值。
- 反向传播计算梯度时,需注意激活函数的导数(如tanh的导数为
1 - tanh²)。
三、神经网络的优化策略
3.1 动量法(Momentum)
模拟物理中的动量,加速收敛并减少震荡:
def momentum_update(gradient, velocity, beta=0.9):
velocity = beta * velocity + (1 - beta) * gradient
return velocity
3.2 Adam优化器
结合动量和自适应学习率,以下是简化实现:
def adam_update(gradient, m, v, t, lr=0.001, beta1=0.9, beta2=0.999, eps=1e-8):
m = beta1 * m + (1 - beta1) * gradient # 一阶矩
v = beta2 * v + (1 - beta2) * (gradient ** 2) # 二阶矩
m_hat = m / (1 - beta1**t) # 偏差修正
v_hat = v / (1 - beta2**t)
return m_hat / (np.sqrt(v_hat) + eps)
应用场景:
- 动量法:适用于损失函数存在局部最优或鞍点。
- Adam:默认首选,尤其适合稀疏数据(如自然语言处理)。
四、实战注意事项
- 学习率选择:过大导致震荡,过小收敛慢。可用学习率衰减策略:
learning_rate = initial_lr / (1 + decay_rate * epoch) - 梯度消失/爆炸:用Batch Normalization或残差连接(ResNet)解决。
- 过拟合:Dropout层或L2正则化。
总结:
梯度下降变种、反向传播和优化策略是训练神经网络的三大支柱。理解其原理后,灵活选择工具(如PyTorch已内置所有优化器),才能在实践中游刃有余。
评论