np.square(Wl) 计算各元素的平方
1 | >>> np.square([-1, 1]) |
np.nansum() 求所有元素和的时候将非数字(NaN)当做 0。
1 | >>> np.nansum([1, np.nan]) |
np.c_[xx.ravel(), yy.ravel()]
np.r_是按行连接两个矩阵,就是把两矩阵上下相加,要求行数相等。
np.c_是按列连接两个矩阵,就是把两矩阵左右相加,要求列数相等。
numpy.ravel((a, order=’C’)是将多维数组降为一维,等同于reshape(-1, order=order)。
1 | >>> x = np.array([[1, 2, 3], [4, 5, 6]]) |
这里介绍解决过拟合的两个方法,一个是使用L2正则化,另一个是使用Dropout正则化。
算法步骤
首先先介绍一个三层神经网络的模型,对此网络进行正则化。
模型
模型参数中,lamdb是L2正则化的参数,keep_prob是Dropout的参数。当lamdb > 0 时,说明使用了L2正则化,这时,前向传播不变,要调用对应的损失函数compute_cost_with_regularization及对应的反向传播函数backward_propagation_with_regularization;当keep_prob != 1 时,说明使用了Dropout,这时,损失函数不变,要调用对应的前向传播函数forward_propagation_with_dropout及对应的反向传播函数backward_propagation_with_dropout。这些函数将会在接下来进行介绍。
1 | def model(X, Y, learning_rate = 0.3, num_iterations = 30000, print_cost = True, lambd = 0, keep_prob = 1): |
L2 正则化
L2正则化依赖以下假设,即具有较小超参数的模型比较大的模型要更简单。
对于L2正则化,在原损失函数后面增加了对超参数W的惩罚项。
$$J_{regularized} = \small \underbrace{-\frac{1}{m} \sum\limits_{i = 1}^{m} \large{(}\small y^{[i]}\log\left(a^{[L][i]}\right) + (1-y^{[i]})\log\left(1- a^{[L][i]}\right) \large{)} }_\text{cross-entropy cost} + \underbrace{\frac{1}{m} \frac{\lambda}{2} \sum\limits_l\sum\limits_k\sum\limits_j W_{k,j}^{[l]2} }_\text{L2 regularization cost} $$
下面我们实现函数compute_cost_with_regularization()。
1 |
|
损失函数发生改变后,反向传播也随之变化,dW1, dW2 和 dW3 的计算公式是发生变化了的,即要添加一个正则项的导数$\frac{d}{dW} ( \frac{1}{2}\frac{\lambda}{m} W^2) = \frac{\lambda}{m} W$。
1 |
|
L2 正则化是我们的结果更加平滑,但是如果超参数 λ 选取的太大的话,就有可能 “oversmooth”, 从而导致模型具有较大的偏差(bias)。
Dropout 正则化
首先实现使用Dropout对应的前向传播函数forward_propagation_with_dropout。我们在第一个和第二个隐藏层使用Dropout,而在输入和输出层不使用。
1 |
|
然后实现反向传播,在反向传播中,以dA1为例,要对dA1 也乘以同样的 D[1],并除以keep_prob。
1 |
|
一个常见的误区就是同时在训练和测试中都使用Dropout,实际上,只能在训练过程中使用Dropout。