在较深的网络,如多层CNN或者非常长的RNN,由于求导的链式法则,有可能会出现梯度消失(Gradient Vanishing)或梯度爆炸(Gradient Exploding )的问题。

原理

问题:为什么梯度爆炸会造成训练时不稳定而且不收敛?
梯度爆炸,其实就是偏导数很大的意思。回想我们使用梯度下降方法更新参数:

损失函数的值沿着梯度的方向呈下降趋势,然而,如果梯度(偏导数)很大话,就会出现函数值跳来跳去,收敛不到最值的情况,如图:

当然出现这种情况,其中一种解决方法是,将学习率αα设小一点,如0.0001。

这里介绍梯度裁剪(Gradient Clipping)的方法,对梯度进行裁剪,论文提出对梯度的L2范数进行裁剪,也就是所有参数偏导数的平方和再开方。

TensorFlow代码

方法一:

optimizer = tf.train.AdamOptimizer(learning_rate=0.001, beta1=0.5)
grads = optimizer.compute_gradients(loss)
for i, (g, v) in enumerate(grads):
if g is not None:
grads[i] = (tf.clip_by_norm(g, 5), v) # 阈值这里设为5
train_op = optimizer.apply_gradients(grads)

其中
optimizer.compute_gradients()返回的是正常计算的梯度,是一个包含(gradient, variable)的列表。

tf.clip_by_norm(t, clip_norm)返回裁剪过的梯度,维度跟t一样。

不过这里需要注意的是,这里范数的计算不是根据全局的梯度,而是一部分的。

方法二:

optimizer = tf.train.AdamOptimizer(learning_rate=0.001, beta1=0.5)
grads, variables = zip(*optimizer.compute_gradients(loss))
grads, global_norm = tf.clip_by_global_norm(grads, 5)
train_op = optimizer.apply_gradients(zip(grads, variables))

这里是计算全局范数,这才是标准的。不过缺点就是会慢一点,因为需要全部梯度计算完之后才能进行裁剪。

总结

当你训练模型出现Loss值出现跳动,一直不收敛时,除了设小学习率之外,梯度裁剪也是一个好方法。

然而这也说明,如果你的模型稳定而且会收敛,但是效果不佳时,那这就跟学习率和梯度爆炸没啥关系了。因此,学习率的设定和梯度裁剪的阈值并不能提高模型的准确率。

TensorFlow的梯度裁剪的更多相关文章

  1. tensorflow 梯度裁剪

    gvs = optimizer.compute_gradients(loss) # 计算出梯度和变量值 capped_gvs = [(tf.clip_by_value(grad, -5e+10, 5e ...

  2. pytorch梯度裁剪(Clipping Gradient):torch.nn.utils.clip_grad_norm

    torch.nn.utils.clip_grad_norm(parameters, max_norm, norm_type=2) 1.梯度裁剪原理(http://blog.csdn.net/qq_29 ...

  3. 梯度裁剪(Clipping Gradient):torch.nn.utils.clip_grad_norm

    torch.nn.utils.clip_grad_norm_(parameters, max_norm, norm_type=2) 1.(引用:[深度学习]RNN中梯度消失的解决方案(LSTM) ) ...

  4. ptorch常用代码梯度篇(梯度裁剪、梯度累积、冻结预训练层等)

    梯度裁剪(Gradient Clipping) 在训练比较深或者循环神经网络模型的过程中,我们有可能发生梯度爆炸的情况,这样会导致我们模型训练无法收敛. 我们可以采取一个简单的策略来避免梯度的爆炸,那 ...

  5. 『TensorFlow』梯度优化相关

    tf.trainable_variables可以得到整个模型中所有trainable=True的Variable,也是自由处理梯度的基础 基础梯度操作方法: tf.gradients 用来计算导数.该 ...

  6. TensorFlow实现梯度下降

    # -*- coding: utf-8 -*- """ Created on Mon Oct 15 17:38:39 2018 @author: zhen "& ...

  7. tensorflow随机梯度下降算法使用滑动平均模型

    在采用随机梯度下降算法训练神经网络时,使用滑动平均模型可以提高最终模型在测试集数据上的表现.在Tensflow中提供了tf.train.ExponentialMovingAverage来实现滑动平均模 ...

  8. 实现属于自己的TensorFlow(二) - 梯度计算与反向传播

    前言 上一篇中介绍了计算图以及前向传播的实现,本文中将主要介绍对于模型优化非常重要的反向传播算法以及反向传播算法中梯度计算的实现.因为在计算梯度的时候需要涉及到矩阵梯度的计算,本文针对几种常用操作的梯 ...

  9. TensorFlow使用记录 (八): 梯度修剪 和 Max-Norm Regularization

    梯度修剪 梯度修剪主要避免训练梯度爆炸的问题,一般来说使用了 Batch Normalization 就不必要使用梯度修剪了,但还是有必要理解下实现的 In TensorFlow, the optim ...

随机推荐

  1. 笔记:认识 head 标签 待 更新中……

    文档的头部描述了文档的各种属性和信息,包括文档的标题等.绝大多数文档头部包含的数据都不会真正作为内容显示给读者. 下面这些标签可用在 head 部分: <head> <title&g ...

  2. 7-12 How Long Does It Take

    Given the relations of all the activities of a project, you are supposed to find the earliest comple ...

  3. android-基础编程-RecyclerView

    以后android-基础编程*都是控件demo里面的,不再累赘重写.直接介绍控件使用. RecyclerView is a more advanced and flexible version of ...

  4. 正确的类引用却显示* cannot be resolved

    eclipse 出现的问题:在一个类中引入自己编写的类竟然说“cannot be resolved”,这非常明显不正常的! 解决办法:很简单,project->clean.我的问题就解决了. 至 ...

  5. Digital Roots—HDU1013 2016-05-06 10:25 85人阅读 评论(0) 收藏

    Digital Roots Time Limit: 2000/1000 MS (Java/Others)    Memory Limit: 65536/32768 K (Java/Others) To ...

  6. java 异步机制与同步机制的区别

    所谓异步输入输出机制,是指在进行输入输出处理时,不必等到输入输出处理完毕才返回.所以异步的同义语是非阻塞(None Blocking). 网上有很多网友用很通俗的比喻  把同步和异步讲解的很透彻 转过 ...

  7. html\css不同长度文本左右对齐 text-align:justify的使用

    在平常的开发过程中,对于text-align一般用到的是left,center,right,这三个属性都不会陌生.然而,对于justify的使用我却是很陌生.首先有个比较简单的例子. 如下代码: &l ...

  8. 那些好用的阅读软件(Windows & Android)

    此文章已添加预览与更新,请您移步到我的新博客 http://t.cn/EXCiCTE 整个2018年就没写过几篇博文,所以写一篇文章算过年啦-哈哈-有部分软件因为年代原因,官网已经消失.或者网络上的资 ...

  9. EF查询返回DataTable

    using (SchoolContext dbCOntext = new SchoolContext()) { string str = "select * from student&quo ...

  10. [学习笔记]CDQ分治和整体二分

    序言 \(CDQ\) 分治和整体二分都是基于分治的思想,把复杂的问题拆分成许多可以简单求的解子问题.但是这两种算法必须离线处理,不能解决一些强制在线的题目.不过如果题目允许离线的话,这两种算法能把在线 ...