机器学习的学习不应该仅仅停留在对scikit-learn or tensorflow(deep learning)框架的调用,而应该着眼于内部的世界,学习机器学习有一段时间了,有必要回头整理一下,下面我们基于线性模型来看
- 标准方程
- 梯度下降
进而来看基于以上两者如何实现模型的训练,基本思想一致,不同的模型大家可以触类旁通
下面我们分布阐述
1.标准方程
标
准
方
程
:
其
实
就
是
求
算
法
模
型
成
本
函
数
最
小
,
即
为
0
的
时
候
的
θ
的
闭
式
解
标准方程:其实就是求算法模型成本函数最小,即为0的时候的\theta的闭式解
标准方程:其实就是求算法模型成本函数最小,即为0的时候的θ的闭式解
这个定义其实很好理解:
下面我们以线性回归进行进一步的论证:
- 1.线性回归的预测模型
y = θ ∗ X y = \theta * X y=θ∗X - 2.那么线性回归的成本函数就是MSE:
M S E ( X , h θ ) = 1 / m ∑ i = 0 m ( θ T ∗ X i − y i ) 2 MSE(X,h_\theta) = 1/m \sum_{i=0}^{m}(\theta^T * Xi - yi)^2 MSE(X,hθ)=1/mi=0∑m(θT∗Xi−yi)2 - 3.接着我们对MSE求导,并令其等于0,这样得到一个权重theta为因变量的闭式解:
θ = ( X T ∗ X ) − 1 ∗ X T ∗ y \theta = (X^T * X)^{-1} * X^T * y θ=(XT∗X)−1∗XT∗y - 4.得到标准方程,模型便可以开始预测了:
y ( p r e d ) = θ ∗ X y(pred) = \theta * X y(pred)=θ∗X
2.梯度下降
梯度下降:可以成为是从初始theta开始,一步步求的成本函数最低点的过程;
θ
(
n
e
x
t
)
=
θ
−
η
∂
m
s
e
∂
θ
\theta(next) = \theta - \eta \frac{\partial mse}{\partial \theta}
θ(next)=θ−η∂θ∂mse
θ
:
权
重
向
量
η
:
学
习
率
∂
m
s
e
∂
θ
:
梯
度
\theta:权重向量 \quad \eta:学习率 \quad \frac{\partial mse}{\partial \theta}:梯度
θ:权重向量η:学习率∂θ∂mse:梯度
其实通过上面的参数我们可以进一步理解梯度下降:
- 梯度下降:通过上面的公式不断更新权重,不断的训练模型,当成本函数达到理想值的时候,停止更新权重,即停止训练模型
2.1:梯度向量的计算:
上面就是梯度下降的图例,以线性回归为例,成本函数的梯度向量也可以通过一个闭式方程进行计算:
∂
m
s
e
∂
θ
=
2
/
m
∗
∑
i
=
1
m
(
θ
∗
X
(
i
)
−
y
(
i
)
)
x
j
(
i
)
\frac{\partial mse}{\partial \theta} = 2/m * \sum_{i=1}^m(\theta * X^{(i)} - y^{(i)})x_j^{(i)}
∂θ∂mse=2/m∗i=1∑m(θ∗X(i)−y(i))xj(i)
∂
m
s
e
∂
θ
=
2
/
m
∗
X
T
∗
(
X
∗
θ
−
y
)
\frac{\partial mse}{\partial \theta} = 2/m * X^T * (X*\theta - y)
∂θ∂mse=2/m∗XT∗(X∗θ−y)
2.2:学习率
学习率在梯度下降的过程中很关键,如果学习率很低,算法需要大量时间才可以收敛;
反之,学习率太高,则会让函数迅速发散最终找不到最优解
所以,学习率做为一个重要的超参数,我们应该通过类似网格搜索等途径获取最佳的学习率,或者可以这样,随着训练次数的提升,有规律的降低学习率:
下面看图例:(第一个是学习率太低,第二个是学习率太高)
梯度下降可以分为3种,主要式通过训练所用到的X的shape级别进行区分:
- 批量梯度下降:每次使用全部的数据进行梯度计算
- 随机梯度下降:每次使用随机的一条数据进行梯度计算
- 小批量梯度下降:每次从数据中随机取出一部分数据进行计算
到这里,我们可以直观的看出机器学习中,梯度下降可以用来优化模型
3.机器学习模型训练过程
下面粘贴一部分tensorflow的代码,(不了解tensorflow可以直接跳过这块代码):
m, n = housing.data.shape
n_epochs = 1000
learning_rate = 0.01
pipeline = Pipeline([
('std_scaler', StandardScaler())
])
scaled_housing_data_plus_bias = pipeline.fit_transform(housing_data_plus_bias)
serialize_data(scaled_housing_data_plus_bias,'scaled_housing_data_plus_bias')
X = tf.constant(scaled_housing_data_plus_bias, dtype=tf.float32, name='X')
y = tf.constant(housing.target.reshape(-1, 1), dtype=tf.float32, name='y')
# 获取初始的theta
theta = tf.Variable(tf.random_uniform([n + 1, 1], -1.0, 1.0), name='theta')
y_pred = tf.matmul(X, theta, name='predictions')
error = y_pred - y
mse = tf.reduce_mean(tf.square(error), name='mse')
gradients = 2 / m * tf.matmul(tf.transpose(X), error)
training_op = tf.assign(theta, theta - learning_rate * gradients)
# 开启会话
init = tf.global_variables_initializer()
with tf.Session() as sess:
sess.run(init)
for epoch in range(n_epochs):
if epoch % 100 == 0:
print('Epoch', epoch, 'MSE = ', mse.eval())
sess.run(training_op)
# training_op.eval()
best_theta = theta.eval()
具体阐述原理:
1.初始化权重向量
θ
\theta
θ,这里的
θ
\theta
θ初始化需要注意,
θ
\theta
θ的shape须为
(
f
e
a
t
u
r
e
s
,
)
(features,)
(features,)
2.接着利用\theta*X求得当前的预测值,进而求的MSE,然后利用下面公式:
∂
m
s
e
∂
θ
=
2
/
m
∗
X
T
∗
(
X
∗
θ
−
y
)
          
θ
(
n
e
x
t
)
=
θ
−
η
∂
m
s
e
∂
θ
\frac{\partial mse}{\partial \theta} = 2/m * X^T * (X*\theta - y)\;\;\;\; \;\theta(next) = \theta - \eta \frac{\partial mse}{\partial \theta}
∂θ∂mse=2/m∗XT∗(X∗θ−y)θ(next)=θ−η∂θ∂mse
更新
θ
\theta
θ,循环往复的重复1,2步骤,直到
M
S
E
MSE
MSE的值调节倒最优,停止更新
θ
\theta
θ,并停止训练
如此这般,基于数据不断训练模型直至模型输出最优:
但是需要注意一点:
由于这个训练过程是基于X来进行训练的,所以我们为了提高效率,需要使用小批量的梯度下降:
eg:每次从数据中取出50条数据进行训练,这样效率大大提高