1. 大数据集学习
在机器学习中,通常情况下我们需要很多的数据让模型进行学习,这样才能让模型学习到更多有用的特征,下图展示了测试集精度随训练集大小变化的曲线,随着训练集大小的增大,精度会不断增大。 但是对于太大的数据集,当我们对参数进行如下的梯度更新时,会造成计算量过大,不易于算法的处理,所以我们需要通过一些方法来处理数据集较大的情况。
θ
j
=
θ
j
?
α
1
m
∑
i
=
1
m
[
h
θ
(
x
(
i
)
)
?
y
(
i
)
]
x
j
(
i
)
\theta_j = \theta_j - \alpha\frac{1}{m}\sum_{i=1}^m\left[ h_\theta(x^{(i)})-y^{(i)}\right]x_j^{(i)}
θj?=θj??αm1?i=1∑m?[hθ?(x(i))?y(i)]xj(i)?
但是当我们要对大规模数据集进行学习之前,我们应该使用 预先检查 的方式检验当前的模型,即首先通过比较小的一部分数据对当前模型的能力进行评估,这时可以会得到如下的两种情况。当使用少量数据集时,模型处于高偏差的状态时,我们可以通过增加数据集的方式来进一步提高模型的性能;但是模型如果处于高方差的状态,我们再增大数据集也不会对模型的性能进一步提高,这时我们应该首先改变模型本身。
2. 随机梯度下降算法
在一般的线性模型、回归模型和神经网络等模型中,我们通常是构建一个代价函数,之后使用梯度下降等算法求解使得代价函数尽可能小的参数,但是当参数量很多时,梯度下降的计算量会变得非常大,所以提出使用改进的 随机梯度下降 算法,这样我们就能将模型应用到大数据集中。
对于线性回归来说,使用梯度下降时,每次更新要对数据集中的所有样本求导,如下所示,每次更新中都包含了从
1
1
1 到
m
m
m 个样本的求和,称这种方式为批量梯度下降(Batch gradient desent),但是当样本个数
m
m
m 非常大时,会造成每次更新计算代价过高。
do{
θ
j
=
θ
j
?
α
1
m
∑
i
=
1
m
[
h
θ
(
x
(
i
)
)
?
y
(
i
)
]
x
j
(
i
)
,
f
o
r
(
j
=
0
,
?
?
,
n
)
\quad\quad \theta_j = \theta_j - \alpha\frac{1}{m}\sum\limits_{i=1}^m\left[ h_\theta(x^{(i)})-y^{(i)}\right]x_j^{(i)},\quad for(j=0,\cdots,n)
θj?=θj??αm1?i=1∑m?[hθ?(x(i))?y(i)]xj(i)?,for(j=0,?,n) } while(!convergence)
通过这种批量梯度下降,每次更新都会让整个假设函数向损失函数最小的方向更新,从而找到全局最优。
为了解决数据集过大时计算量增大的问题,这里使用随机梯度下降算法(Stochastic gradient descent),相比于批量梯度下降算法每次计算相对于所有样本的代价函数,这里改变为相对于一个样本的梯度对参数进行更新。
对于线性回归模型,整个数据集的代价函数可以表示如下:
J
t
r
a
i
n
(
θ
)
=
1
2
m
∑
i
=
1
m
[
h
θ
(
x
(
i
)
)
?
y
(
i
)
]
2
=
1
m
∑
i
=
1
m
c
o
s
t
[
θ
,
(
x
(
i
)
,
y
(
i
)
)
]
\begin{aligned} J_{train}(\theta) & =\frac{1}{2m}\sum_{i=1}^m\left[h_{\theta}(x^{(i)})-y^{(i)}\right]^2\\ & = \frac{1}{m}\sum_{i=1}^m cost[\theta,(x^{(i)},y^{(i)})] \end{aligned}
Jtrain?(θ)?=2m1?i=1∑m?[hθ?(x(i))?y(i)]2=m1?i=1∑m?cost[θ,(x(i),y(i))]?
其中
c
o
s
t
cost
cost 表示模型相对于一个样本
(
x
(
i
)
,
y
(
i
)
)
(x^{(i)},y^{(i)})
(x(i),y(i)) 的代价,表示如下:
c
o
s
t
[
θ
,
(
x
(
i
)
,
y
(
i
)
)
]
=
1
2
[
h
θ
(
x
(
i
)
)
?
y
(
i
)
]
2
cost[\theta,(x^{(i)},y^{(i)})]=\frac{1}{2}\left[h_\theta(x^{(i)})-y^{(i)}\right]^2
cost[θ,(x(i),y(i))]=21?[hθ?(x(i))?y(i)]2
随机梯度下降算法可以表示如下:
Repeat{
f
o
r
?
i
=
1
,
?
?
,
m
{
\quad\quad for\ i=1,\cdots,m\{
for?i=1,?,m{
θ
j
=
θ
j
?
α
?
?
θ
j
c
o
s
t
[
θ
,
(
x
(
i
)
,
y
(
i
)
)
]
=
θ
j
?
α
[
h
θ
(
x
(
i
)
)
?
y
(
i
)
]
x
j
(
i
)
,
f
o
r
(
j
=
0
,
?
?
,
n
)
\quad\quad \quad\quad \theta_j = \theta_j - \alpha \frac{\partial}{\partial \theta_j}cost[\theta,(x^{(i)},y^{(i)})]= \theta_j - \alpha\left[ h_\theta(x^{(i)})-y^{(i)}\right]x_j^{(i)},\quad for(j=0,\cdots,n)
θj?=θj??α?θj???cost[θ,(x(i),y(i))]=θj??α[hθ?(x(i))?y(i)]xj(i)?,for(j=0,?,n)
}
\quad\quad \}
} }
在一次 repeat 中,我们只需要将数据集中的所有样本遍历一遍,用每个样本对分别对每个参数
θ
j
\theta_j
θj? 进行更新,也就是让模型每次拟合一个样本。通常情况下,我们只需要一次 repeat 就能找到使代价函数最小的参数,在最差的情况也只需要
1
?
10
1-10
1?10 次 repeat 。
所以整个随机梯度下降的过程如下:
- 随机打乱所有的训练集样本。因为我们要循环遍历所有的样本,所以我们希望每次随机的拟合一个样本,为了防止样本是根据某种结构排列的,所以我们首先对数据集进行随机排序。
- 使用上面的随机梯度下降算法对模型更新,不断更新计算其中的每个参数。
使用随机梯度下降时,学习得到的参数使得代价函数呈现随机而迂回的方向向最小点前进。而批量梯度下降算法是直接向最小点前进。 随机梯度下降算法并不是直接收敛到全局最小值,而是在全局最小值形成的一个范围内反复震荡,最终逐渐接近全局最小值,所以最后得到的只是全局最小值的近似值,但是一般情况下这个近似值已经能够满足我们的要求了。
3. Mini-batch 梯度下降
Mini-batch 梯度下降算法是介于批量梯度下降和随机梯度下降算法之间的更新方式,在整个算法中,每次选择
b
=
2
?
100
b=2-100
b=2?100 个样本对参数进行更新。
如,对于有
m
=
1000
m=1000
m=1000 个样本的数据集,如果我们选择每次更新需要的样本数量
b
=
10
b=10
b=10,那么 Mini-batch 梯度下降的过程可以表示如下:
Repeat{
f
o
r
?
i
=
1
,
11
,
21
,
32
,
?
?
,
991
{
\quad for\ i = 1,11,21,32,\cdots,991\{
for?i=1,11,21,32,?,991{
θ
j
=
θ
j
?
α
1
10
∑
k
=
i
i
+
9
[
h
θ
(
x
(
k
)
)
?
y
(
k
)
]
x
j
(
k
)
,
f
o
r
(
j
=
0
,
?
?
,
n
)
\quad\quad \theta_j = \theta_j - \alpha\frac{1}{10}\sum\limits_{k=i}^{i+9}\left[ h_\theta(x^{(k)})-y^{(k)}\right]x_j^{(k)},\quad for(j=0,\cdots,n)
θj?=θj??α101?k=i∑i+9?[hθ?(x(k))?y(k)]xj(k)?,for(j=0,?,n)
}
\quad \}
} }
相比于梯度下降,其减少了迭代中的计算量;通过向量化的方式,可以实现比随机梯度下降算法更少的计算量。
4. 算法收敛的判断与学习率的选择
4.1 收敛判断
在批量梯度下降中,我们对模型是否达到收敛是通过每次循环中计算如下的代价函数实现的:
J
t
r
a
i
n
(
θ
)
=
1
2
m
∑
i
=
1
m
[
h
θ
(
x
(
i
)
)
?
y
(
i
)
]
2
J_{train}(\theta)=\frac{1}{2m}\sum_{i=1}^m\left[h_{\theta}(x^{(i)})-y^{(i)}\right]^2
Jtrain?(θ)=2m1?i=1∑m?[hθ?(x(i))?y(i)]2
但是当训练集中的样本数量
m
m
m 太大时,计算上式的代价函数时间会非常长,所以我们使用下面的方式对收敛进行判断。
因为在随机梯度下降中每次是根据一个样本的代价来对参数进行更新的,所以我们可以在每次更新之前,用已经得到的模型
h
θ
(
x
)
h_{\theta}(x)
hθ?(x),对当前的样本
(
x
(
i
)
,
y
(
i
)
)
(x^{(i)},y^{(i)})
(x(i),y(i)) 通过以下方式计算损失,之后再使用
(
x
(
i
)
,
y
(
i
)
)
(x^{(i)},y^{(i)})
(x(i),y(i)) 更新样本。
c
o
s
t
[
θ
,
(
x
(
i
)
,
y
(
i
)
)
]
=
1
2
[
h
θ
(
x
(
i
)
)
?
y
(
i
)
]
2
cost[\theta,(x^{(i)},y^{(i)})]=\frac{1}{2}\left[h_\theta(x^{(i)})-y^{(i)}\right]^2
cost[θ,(x(i),y(i))]=21?[hθ?(x(i))?y(i)]2
我们可以选择每迭代
1000
1000
1000 个样本,将根据这些样本计算得到的代价累加后求平均,得到代价的变化曲线图,这样就能对模型的收敛进行判断了。
下图展示了不同迭代大小和学习率对代价函数值的影响,可以发现相比于蓝色曲线,如果我们减小学习率,可以得到算法的学习速度变得更慢了,并且能够收敛到更小的代价值(因为随机梯度下降只是收敛到最小值的周围,所以损失是波动的)。而如果增大计算代价的迭代大小,即每 5000 个样本计算一次代价,会得到更加平缓的绿色曲线。 但是如果得到的代价曲线如下图所示,就需要减少学习率以提高模型的性能。
4.2 学习率的选择
在一般的情况下,学习率
α
\alpha
α 都可以选择为一个不变的常数,但是随机梯度下降算法会使代价函数在最小值附近不断波动,只能很接近最小值。
为了使代价函数更接近最小值,我们可以使
α
\alpha
α 随着迭代次数不断地减少,如通过下式减少学习率:
α
=
c
o
n
s
t
1
i
t
e
r
a
t
i
o
n
N
u
m
b
e
r
+
c
o
n
s
t
2
\alpha = \frac{const1}{iteration Number + const2}
α=iterationNumber+const2const1?
即设置两个常数
c
o
n
s
t
1
const1
const1 和
c
o
n
s
t
2
const2
const2 。引入参数会使算法的复杂度更大,但是也会使最终的结果收敛到更接近代价最小值。
一般情况下设置
α
\alpha
α 为常数已经能够满足我们的要求。
5. 在线学习
对于不断有新数据的情况,我们可以构建**在线学习(Online learning)**模型,这种模型可以不断地对新产生的数据学习,自适应的改变参数。
例如,对于一个在线寄件服务,我们可以根据用户的特征给出一个价格,之后用户可能选择接受
y
=
1
y=1
y=1 ,或不接受
y
=
0
y=0
y=0,这时我们就得到一个样本,其数据
x
x
x 包括用户的一些特征和我们给出的预测价格,标签
y
y
y 表明了用户是否接受。
这时我们就可以根据得到的这个样本执行如下更新:
θ
j
=
θ
j
?
α
[
h
θ
(
x
)
?
y
]
x
j
,
(
j
=
0
,
?
?
,
n
)
\theta_j = \theta_j - \alpha[h_\theta(x)-y]x_j\quad ,(j=0,\cdots,n)
θj?=θj??α[hθ?(x)?y]xj?,(j=0,?,n)
当来了一个新用户时,我们可以根据用户的信息和自己网站的相关信息,计算出用户接受当前推荐信息的概率
p
(
y
=
1
∣
x
;
θ
)
p(y=1|x;\theta)
p(y=1∣x;θ),这样就可以根据概率为用户进行推荐。根据推荐的结果和用户的反馈,我们就能继续对模型进行优化了。
通过这种在线学习的方式,模型可以自适应的变化以满足用户的偏好,因为我们的模型是不断模拟新数据的,当用户的偏好发生了变化,得到的数据也会变化,模型就会对新数据进行学习,实现自适应的改变模型。
6. MapReduce
在批量梯度下降中,当
m
m
m 非常大时,我们可以选择通过多台主机同时进行计算,通过并行实现加速。
对于模型中参数的更新公式:
θ
j
=
θ
j
?
α
1
400
∑
i
=
1
400
[
h
θ
(
x
(
i
)
)
?
y
(
i
)
]
x
j
(
i
)
\theta_j = \theta_j - \alpha\frac{1}{400}\sum_{i=1}^{400}[h_{\theta}(x^{(i)})-y^{(i)}]x_j^{(i)}
θj?=θj??α4001?i=1∑400?[hθ?(x(i))?y(i)]xj(i)?
对于
m
=
400
m=400
m=400 个样本,如果我们有
4
4
4 台主机,我们就可以将所有样本分为四份,每份将其中的一份数据使用一台电脑计算梯度,可以得到四个结果:
t
e
m
p
j
(
1
)
=
∑
i
=
1
100
[
h
θ
(
x
(
i
)
)
?
y
(
i
)
]
x
j
(
i
)
t
e
m
p
j
(
2
)
=
∑
i
=
101
200
[
h
θ
(
x
(
i
)
)
?
y
(
i
)
]
x
j
(
i
)
t
e
m
p
j
(
3
)
=
∑
i
=
201
300
[
h
θ
(
x
(
i
)
)
?
y
(
i
)
]
x
j
(
i
)
t
e
m
p
j
(
4
)
=
∑
i
=
301
400
[
h
θ
(
x
(
i
)
)
?
y
(
i
)
]
x
j
(
i
)
\begin{aligned} temp_j^{(1)} &= \sum_{i=1}^{100} [h_{\theta}(x^{(i)})-y^{(i)}]x_j^{(i)} \\ temp_j^{(2)} &= \sum_{i=101}^{200} [h_{\theta}(x^{(i)})-y^{(i)}]x_j^{(i)} \\ temp_j^{(3)} &= \sum_{i=201}^{300} [h_{\theta}(x^{(i)})-y^{(i)}]x_j^{(i)} \\ temp_j^{(4)} &= \sum_{i=301}^{400} [h_{\theta}(x^{(i)})-y^{(i)}]x_j^{(i)} \end{aligned}
tempj(1)?tempj(2)?tempj(3)?tempj(4)??=i=1∑100?[hθ?(x(i))?y(i)]xj(i)?=i=101∑200?[hθ?(x(i))?y(i)]xj(i)?=i=201∑300?[hθ?(x(i))?y(i)]xj(i)?=i=301∑400?[hθ?(x(i))?y(i)]xj(i)??
最终将结果汇总到中心主机,使用如下的表达式对参数进行更新:
θ
j
=
θ
j
?
α
1
400
[
t
e
m
p
j
(
1
)
+
t
e
m
p
j
(
2
)
+
t
e
m
p
j
(
3
)
+
t
e
m
p
j
(
4
)
]
,
(
j
=
0
,
?
?
,
n
)
\theta_j = \theta_j - \alpha\frac{1}{400}[temp_j^{(1)} +temp_j^{(2)} + temp_j^{(3)} +temp_j^{(4)} ],\quad (j=0,\cdots,n)
θj?=θj??α4001?[tempj(1)?+tempj(2)?+tempj(3)?+tempj(4)?],(j=0,?,n)
计算的示意图表示如下: 只要机器学习的算法可以用多个函数的求和表达,那么我们就能使用这种 MapReduce 方法对整个计算过程加速,实现更高效的计算。
7. 机器学习中的一些方法
- 流水线模块化设计整个机器学习系统
- 利用滑动窗口的思想检测不同的图片区域
- 通过天花板分析的方法选择优化哪个模块
|