深层神经网络进行Gradient Check的时候注意delta的大小
2017-02-16 20:07
246 查看
神经网络的Backward Pass实现是比较容易出错的,一个不错的做法是实现一个神经网络之后,利用Numeric的方法计算一个粗略的梯度,和你实际上算出来的梯度进行比对,如果差的不多,就说明你实现对了。
前两天做CS231n作业的时候遇到了一个特别奇怪的事,我实现了一个N层卷积层,之后跟M层FC-Relu层的简单神经网络,指定N=1,M=2之后,死活过不了Gradient Check,并且永远是FC层的第二层的bias出错,其他参数都完全正确:
查了好几天,百思不得其解,我以为是不是又出现了谁的cache被悄悄了修改的情况,但是打断点进去以后发现一切输入都非常正常。经过很长时间的debug无果以后,我开始怀疑是不是标答有问题。这个时候我突然注意到,在输入FC1,进行完XW+b之后,输出给Relu1的X是这样的:
我们可以看到,这个X都是1e-8级别的,非常小,但是Gradient Check的时候,delta的值却是1e-6,其量级已经与X相当,所以当然得不出正确的结果。
究其原因,这个ConvNet在初始化的时候采用的是从一个均值为0,标准差为weight_scale的正态分布中采样参数的。当时的weight_scale设的是1e-3,因此X每过一层,大约都会减少1000倍。随着层数的深入,值也就会越来越小。当到了第3层以后,与一个1e-6的值相加,自然就会出错。
我尝试调小了delta的值到1e-8,但是结果变成所有的梯度都不对了。我猜是因为这么小的delta不太能准确计算出梯度了。
既然减小delta不行,那么就将weight_scale调大好了,调大到1之后就顺利Pass了Gradient Check。
前两天做CS231n作业的时候遇到了一个特别奇怪的事,我实现了一个N层卷积层,之后跟M层FC-Relu层的简单神经网络,指定N=1,M=2之后,死活过不了Gradient Check,并且永远是FC层的第二层的bias出错,其他参数都完全正确:
num_inputs = 2 input_dim = (3, 16, 16) reg = 0.0 num_classes = 10 X = np.random.randn(num_inputs, *input_dim) y = np.random.randint(num_classes, size=num_inputs) model = ConvNet(num_filters=[3], filter_size=[3], input_dim=input_dim, hidden_dim=[7, 7], dtype=np.float64) loss, grads = model.loss(X, y) for param_name in sorted(grads): f = lambda _: model.loss(X, y)[0] param_grad_num = eval_numerical_gradient(f, model.params[param_name], verbose=False, h=1e-6) #h就是delta,计算公式是d = (f(x+h)-f(x-h))/2h e = rel_error(param_grad_num, grads[param_name]) print '%s max relative error: %e' % (param_name, rel_error(param_grad_num, grads[param_name]))
W_conv0 max relative error: 2.488318e-02 W_fc0 max relative error: 3.070288e-02 W_fc1 max relative error: 1.011455e-02 W_soft max relative error: 5.722041e-03 b_conv0 max relative error: 3.798044e-03 b_fc0 max relative error: 6.489261e-05 b_fc1 max relative error: 1.000000e+00 b_soft max relative error: 9.867731e-10
查了好几天,百思不得其解,我以为是不是又出现了谁的cache被悄悄了修改的情况,但是打断点进去以后发现一切输入都非常正常。经过很长时间的debug无果以后,我开始怀疑是不是标答有问题。这个时候我突然注意到,在输入FC1,进行完XW+b之后,输出给Relu1的X是这样的:
[[ 7.29069965e-08 -2.22044158e-07 -1.74749819e-08 -2.84726995e-08] [ 1.43855178e-07 -3.39216429e-07 1.75782951e-08 -2.42950271e-08]]
我们可以看到,这个X都是1e-8级别的,非常小,但是Gradient Check的时候,delta的值却是1e-6,其量级已经与X相当,所以当然得不出正确的结果。
究其原因,这个ConvNet在初始化的时候采用的是从一个均值为0,标准差为weight_scale的正态分布中采样参数的。当时的weight_scale设的是1e-3,因此X每过一层,大约都会减少1000倍。随着层数的深入,值也就会越来越小。当到了第3层以后,与一个1e-6的值相加,自然就会出错。
我尝试调小了delta的值到1e-8,但是结果变成所有的梯度都不对了。我猜是因为这么小的delta不太能准确计算出梯度了。
既然减小delta不行,那么就将weight_scale调大好了,调大到1之后就顺利Pass了Gradient Check。
相关文章推荐
- 训练深度神经网络的时候需要注意的一些小技巧
- 训练深度神经网络的时候需要注意的一些小技巧
- 训练深度神经网络的时候需要注意的一些小技巧
- 神经网络中的激活函数——加入一些非线性的激活函数,整个网络中就引入了非线性部分,sigmoid 和 tanh作为激活函数的话,一定要注意一定要对 input 进行归一话,但是 ReLU 并不需要输入归一化
- 训练深度神经网络的时候需要注意的一些小技巧
- 训练深度神经网络的时候需要注意的一些小技巧【转载】
- 训练深度神经网络的时候需要注意的技巧
- 训练深度神经网络的时候需要注意的一些小技巧
- 神经网络与深度学习 1.5 使用梯度下降算法进行学习
- 吴恩达(Andrew Ng)深度学习工程师笔记 - 第一门课-神经网络和深度学习-第一周深度学习概论-第三节:用神经网络进行监督学习
- 第四周深层神经网络
- 理解深层神经网络中的迁移学习及TensorFlow实现
- 构建多层感知器神经网络对数字图片进行文本识别
- 深层神经网络——线性模型的局限性
- 深层神经网络——多层网络解决异或运算
- 深层神经网络
- Coursera吴恩达《神经网络与深度学习》课程笔记(5)-- 深层神经网络
- 第2次课改善深层神经网络:超参数优化、正则化以及优化 - week2 优化算法
- 第2次课改善深层神经网络:超参数优化、正则化以及优化 - week3 超参数调试、Batch正则化和程序框架
- 深度学习——利用学习框架TensorFlow搭建深层神经网络DNN