Improving Deep Neural Networks[3]
对吴恩达老师的《优化深度神经网络》课程作业知识进行总结。
文章目录
梯度检测 Gradient Checking
首先,明确梯度检测的目的:梯度检测是一个用于检测在反向传播过程中,是否正确计算了梯度的方法。在本节中,吴恩达老师举了一个例子说明梯度检测的使用情况:
在公司或团队的工作中,你的上司要求你证明自己的反向传播部分计算的导数都是正确的,此时,就需要利用梯度检测来进行确认证明了。
1 梯度检测的工作原理
反向传播过程中,我们会计算J关于各个参数的梯度: ∂ J ∂ θ \dfrac{\partial J}{\partial \theta} ∂θ∂J,其中 θ \theta θ是有关的参数。
前向传播的结构非常简单,几乎没有计算的过程,因此,我们几乎可以100%认为前向传播得到的 J J J是可靠的。
梯度检测正是利用 J J J来进行检测的。
梯度的计算公式定义如下:
∂
J
∂
θ
=
lim
ε
→
0
J
(
θ
+
ε
)
−
J
(
θ
−
ε
)
2
ε
\frac{\partial J}{\partial \theta}=\lim _{\varepsilon \rightarrow 0} \frac{J(\theta+\varepsilon)-J(\theta-\varepsilon)}{2 \varepsilon}
∂θ∂J=ε→0lim2εJ(θ+ε)−J(θ−ε)
可以知道,公式左侧的梯度正是我们需要验证的;
在前向传播得到 J J J之后,我们可以取一个足够小的值 ϵ \epsilon ϵ,依据公式右侧的式子计算并验证。
2 N维梯度检测 N-dimensional Gradient Check
根据工作原理,使用以下代码进行检测:
def gradient_check_n(parameters, gradients, X, Y, epsilon = 1e-7):
# Set-up variables
parameters_values, _ = dictionary_to_vector(parameters)
grad = gradients_to_vector(gradients)
num_parameters = parameters_values.shape[0]
J_plus = np.zeros((num_parameters, 1))
J_minus = np.zeros((num_parameters, 1))
gradapprox = np.zeros((num_parameters, 1))
# Compute gradapprox
for i in range(num_parameters):
theta_plus = np.copy(parameters_values)
theta_plus[i][0] += epsilon
J_plus[i], _ =
forward_propagation_n(X, Y, vector_to_dictionary(theta_plus))
theta_minus = np.copy(parameters_values)
theta_minus[i][0] -= epsilon
J_minus[i], _ =
forward_propagation_n(X, Y, vector_to_dictionary(theta_minus))
# Compute gradapprox[i]
gradapprox[i] = (J_plus[i] - J_minus[i]) / (2 * epsilon)
difference =
(np.linalg.norm(grad - gradapprox)) /
(np.linalg.norm(grad) + np.linalg.norm(gradapprox))
if difference > 1e-7:
...
return difference
在完成grad计算(反向传播)以及gradapprox计算(梯度定义)后,利用欧氏距离进行度量:
difference
=
∥
grad
−
gradapprox
∥
2
∥
grad
∥
2
+
∥
gradapprox
∥
2
\text {difference}=\frac{\| \text { grad }-\text {gradapprox} \|_{2}}{\| \text { grad }\left\|_{2}+\right\| \text { gradapprox } \|_{2}}
difference=∥ grad ∥2+∥ gradapprox ∥2∥ grad −gradapprox∥2
在代码中,利用了 np.linalg.norm()
计算范数。
3 总结 Conclusion
吴恩达老师在本节末提到:
- 梯度检测是非常缓慢、低效的(因为gradapprox的计算),因此在迭代训练中不会将梯度检测加入每一次迭代,而是在一些特定时候进行检测。
- 不要和Dropout一起使用。Dropout会关闭神经元,会使得部分情况下无法检测到错误/误判错误,一般地,我们在检测无误后再添加Dropout正则化。
上一篇:Improving Deep Neural Networks[2]
下一篇:
2019/10 Karl