神经网络优化--滑动平均

滑动平均:记录了一段时间内模型中所有参数w和b各自的平均值。利用滑动平均值可以增强模型的泛化能力。
滑动平均值(影子)计算公式:
影子 = 衰减率 * 影子 + (1 - 衰减率) * 参数
其中,影子初值 = 参数初值
在这里插入图片描述
用Tensorflow函数表示为:
ema = tf.train.ExponentialMovingAverage(MOVING_AVERAGE_DECAY,global_step)
其中,MOVING_AVERAGE_DECAY表示滑动平均衰减率,一般会给接近1的值,global_step表示当前训练了多少轮。
ema_op = ema.apply(tf.trainable_variables())
其中,ema.apply()函数实现对括号内参数求滑动平均,tf.trainable_variables()函数实现把所有待训练参数汇总为列表。
with tf.control_dependencies([train_step,ema_op]):
train_op = tf.no_op(name = ‘train’)
其中,该函数实现将滑动平均和训练过程同步运行。
查看模型中参数的平均值,可以用ema.average()函数。
例如:
在神经网络模型中,将MOVING_AVERAGE_DECAY设置为0.99,参数w1设置为0,w1的滑动平均值设置为0.
1、开始时,轮数global_step设置为0,参数w1更新为1,则w1的滑动平均值为:
在这里插入图片描述
2、当轮数global_step设置为100时,参数w1更新为10,以下代码global_step保持为100,每次执行滑动平均操作影子值更新,则滑动平均值变为:
在这里插入图片描述
3、再次运行,参数w1更新为1.644,则滑动平均值变为:
在这里插入图片描述
4、再次运行,参数w1更新为2.328,则滑动平均值:
w1滑动平均值=2.956

代码如下:

#coding:utf-8
import tensorflow as tf
#1.定义变量及滑动平均类
#定义一个32位浮点变量,初始值为0.0,这个代码就是不断更新w1参数,滑动平均做了个w1的影子
w1 = tf.Variable(0,dtype = tf.float32)
#定义num_updates(NN的迭代轮数),初始值为0,不可被优化(训练),这个参数不训练
global_step = tf.Variable(0,trainable=Flase)
#实例化滑动平均类,给衰减率为0.99,当前轮数global_step
MOVING_AVERAGE_DECAY = 0.99
ema = tf.train.ExponentialMovingAverage(MOVING_AVERAGE_DECAY,global_step)
#ema.apply后的括号里是更新列表,每次运行sess.run(ema_op)时,对更新列表中的元素求滑动平均值。
#在实际应用中会使用tf.trainable_variables()自动将所有待训练的参数汇总为列表
#ema_op = ema.apply([w1])
ema_op = ema.apply(tf.trainable_averables())

#2.查看不同迭代中变量取值的变化。
with tf.Session() as sess:
	#初始化
	init_op = tf.global_variables_initializer()
	sess.run(init_op)
	#用ema.average(w1)获取w1滑动平均值 (要运行多个节点,作为列表中的元素列出,卸载sess.run中)
	#打印出当前参数w1和w2滑动平均值
	print sess.run([w1,ema.average(w1)])
	
	#参数w1的值给1
	sess.run(tf.assign(w1,1))
	sess.run(ema_op)
	print sess.run([w1,ema.average(w1)])

	#更新step和w1的值,模拟出100轮迭代后,参数w1变为10
	sess.run(tf.assign(global_step,100))
	sess.run(tf.assign(w1,10))
	sess.run(ema_op)
	print sess.run([w1,ema.average(w1)])
	
	#每次sess.run会更新一次w1的滑动平均值
	sess.run(ema_op)
	print sess.run([w1,ema.average(w1)])

	sess.run(ema_op)
	print sess.run([w1,ema.average(w1)])

	sess.run(ema_op)
	print sess.run([w1,ema.average(w1)])
	
	sess.run(ema_op)
	print sess.run([w1,ema.average(w1)])
	
	sess.run(ema_op)
	print sess.run([w1,ema.average(w1)])
	
	sess.run(ema_op)
	print sess.run([w1,ema.average(w1)])

运行程序,结果如下:
在这里插入图片描述
从运行结果可知,最初参数w1和滑动平均值都是0;参数w1设定为1后,滑动平均值变为0.9;当迭代轮数更新为100轮时,参数w1更新为10后,滑动平均值变为1644。随后每执行一次,参数w1的滑动平均值都向参数w1靠近。可见,滑动平均追随参数的变化而变化。

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

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值