inverted_dropout

最近在B站看沐神的动手学深度学习视频,记录一下学习过程
查看本文的jupyter notebook格式,更加清晰美观哦!

丢弃法

除了权重衰减以外,深度学习常常使用丢弃法(dropout)来应对过拟合问题。丢弃法有一些不同的变体。本文中提到的丢弃法特指倒置丢弃法(inverted dropout)
当对隐藏层使用丢弃法时,隐藏单元将有一定的概率被丢弃。设丢弃概率为p,丢弃概率是丢弃法的超参数。具体来说,设随机变量,εi为0或1的概率分别为p和1-p。使用丢弃法时,重新计算隐藏单元,hi’=εi*hi/(1-p)。由于E(εi)=1-p,因此E(hi’)=E(εi)*hi/(1-p)=hi。由此可知,丢弃法并不改变输入值的期望。
由于在训练中,隐藏层的神经元是随机丢弃的,即每个神经元的输出都可能被清零,输出层的计算无法过度依赖任何一个神经元,从而在训练模型时起到正则化的作用,并可以用来应对过拟合。在测试模型时,为了得到更加确定性的结果,一般不使用丢弃法。
%matplotlib inline
import d2lzh as d2l
from mxnet import gluon, nd, autograd, init
from mxnet.gluon import loss as gloss, data as gdata, nn
测试nd.random.uniform函数的作用
w = nd.random.uniform(0, 1, shape=(3,5))
w
[[0.5488135  0.5928446  0.71518934 0.84426576 0.60276335]
 [0.8579456  0.5448832  0.8472517  0.4236548  0.6235637 ]
 [0.6458941  0.3843817  0.4375872  0.2975346  0.891773  ]]
<NDArray 3x5 @cpu(0)>
mask = w<0.6
mask
[[1. 1. 0. 0. 0.]
 [0. 1. 0. 1. 0.]
 [0. 1. 1. 1. 0.]]
<NDArray 3x5 @cpu(0)>
mask*w
[[0.5488135 0.5928446 0.        0.        0.       ]
 [0.        0.5448832 0.        0.4236548 0.       ]
 [0.        0.3843817 0.4375872 0.2975346 0.       ]]
<NDArray 3x5 @cpu(0)>

从零开始实现

def dropout(X, drop_prob):
    """以drop_prob的概率随机丢弃NDArray类型的X中的元素"""
    assert 0<=drop_prob<=1
    keep_prob = 1-drop_prob
    # 这种情况下,把全部元素都丢弃
    if keep_prob==0:
        return X.zeros_like()
    mask = nd.random.uniform(0, 1, X.shape) < keep_prob
    return mask*X / keep_prob
运行几个例子,测试dropout函数。其中丢弃概率分别为0, 0.5, 1
X = nd.arange(16).reshape(2,8)
dropout(X, 0)
[[ 0.  1.  2.  3.  4.  5.  6.  7.]
 [ 8.  9. 10. 11. 12. 13. 14. 15.]]
<NDArray 2x8 @cpu(0)>
dropout(X, 0.5)
[[ 0.  2.  4.  0.  0.  0. 12.  0.]
 [ 0.  0. 20.  0.  0. 26.  0.  0.]]
<NDArray 2x8 @cpu(0)>
dropout(X, 1)
[[0. 0. 0. 0. 0. 0. 0. 0.]
 [0. 0. 0. 0. 0. 0. 0. 0.]]
<NDArray 2x8 @cpu(0)>
定义模型参数。使用Fashion_MNIST数据集,定义两层隐藏层的多层感知机,其中两个隐藏层的单元个数都是256
num_inputs, num_outputs, num_hiddens1, num_hiddens2 = 784, 10, 256, 256

W1 = nd.random.normal(scale=0.01, shape=(num_inputs , num_hiddens1))
b1 = nd.zeros(shape=(num_hiddens1))
W2 = nd.random.normal(scale=0.01, shape=(num_hiddens1 , num_hiddens2))
b2 = nd.zeros(shape=(num_hiddens2))
W3 = nd.random.normal(scale=0.01, shape=(num_hiddens2 , num_outputs))
b3 = nd.zeros(shape=(num_outputs))

params = [W1, b1, W2, b2, W3, b3]
for param in params:
    param.attach_grad()
定义模型。通常的建议是靠近输入层的丢弃概率设置的小一点。在这个实验中,把第一个隐藏层的丢弃概率设置为0.2, 第二个隐藏层的丢弃概率设置为0.5。通过is_training函数判断运行模式为训练还是测试,并只需要在训练模式下使用丢弃法。
drop_prob1, drop_prob2 = 0.2, 0.5
def net(X):
    X = X.reshape((-1, num_inputs))
    H1 = (nd.dot(X, W1)+b1).relu()
    if autograd.is_training():
        H1 = dropout(H1, drop_prob1)
    H2 = (nd.dot(H1, W2)+b2).relu()
    if autograd.is_training():
        H2 = dropout(H2, drop_prob2)
    return nd.dot(H2, W3)+b3
训练和测试模型
num_epochs, lr, batch_size = 5, 0.5, 256
loss = gloss.SoftmaxCrossEntropyLoss()
train_iter, test_iter = d2l.load_data_fashion_mnist(batch_size)
d2l.train_ch3(net, train_iter, test_iter, loss, num_epochs, batch_size, params, lr)
epoch 1, loss 1.1165, train acc 0.562, test acc 0.785
epoch 2, loss 0.5763, train acc 0.784, test acc 0.810
epoch 3, loss 0.4883, train acc 0.822, test acc 0.854
epoch 4, loss 0.4424, train acc 0.839, test acc 0.858
epoch 5, loss 0.4166, train acc 0.849, test acc 0.864

简洁实现

在Gluon中,只需要在全连接层后添加Dropout层并指定丢弃概率。在训练模型时,Dropout层将以指定的丢弃概率随机丢弃上一层的输出元素;在测试模型时,Dropout层并不发挥作用。
net = nn.Sequential()
net.add(nn.Dense(256,activation='relu'),
       nn.Dropout(drop_prob1), # 在第一个全连接层后添加丢弃层
       nn.Dense(256, activation='relu'),
       nn.Dropout(drop_prob2), # 在第二个全连接层后添加丢弃层
       nn.Dense(10))
net.initialize(init.Normal(sigma=0.01))
训练并测试模型
trainer = gluon.Trainer(net.collect_params(), 'sgd', {'learning_rate':lr})
d2l.train_ch3(net, train_iter, test_iter, loss, num_epochs, batch_size, None, None, trainer)
epoch 1, loss 1.1389, train acc 0.558, test acc 0.783
epoch 2, loss 0.5777, train acc 0.786, test acc 0.831
epoch 3, loss 0.4957, train acc 0.819, test acc 0.847
epoch 4, loss 0.4498, train acc 0.836, test acc 0.857
epoch 5, loss 0.4213, train acc 0.846, test acc 0.863

forward propagation, backward propagation and computational graph given in this link.

http://zh.gluon.ai/chapter_deep-learning-basics/backprop.html

  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值