登录
登录 注册新账号
注册
已有账号登录
tf.nn.dropout的使用
Eric Wang 阅读 896 次
10月10日发布

  神经网络在设置的神经网络足够复杂的情况下,可以无限逼近一段非线性连续函数,但是如果神经网络设置的足够复杂,将会导致过拟合(overfitting)的出现,就好像下图这样。

  看到这个蓝色曲线,我就知道:

  很明显蓝色曲线是overfitting的结果,尽管它很好的拟合了每一个点的位置,但是曲线是歪歪曲曲扭扭捏捏的,这个的曲线不具有良好的鲁棒性,在实际工程实验中,我们更希望得到如黑色线一样的曲线。

  tf.nn.dropout函数介绍

  tf.nn.dropout是tensorflow的好朋友,它的作用是为了减轻过拟合带来的问题而使用的函数,它一般用在每个连接层的输出。

  Dropout就是在不同的训练过程中,按照一定概率使得某些神经元停止工作。也就是让每个神经元按照一定的概率停止工作,这次训练过程中不更新权值,也不参加神经网络的计算。但是它的权重依然存在,下次更新时可能会使用到它。

  def dropout(x, keepprob, noiseshape=None, seed=None, name=None)

  x 一般是每一层的输出

  keepprob,保留keepprob的神经元继续工作,其余的停止工作与更新

  在实际定义每一层神经元的时候,可以加入dropout。

  def addlayer(inputs,insize,outsize,nlayer,activationfunction = None,keepprob = 1):

  layername = 'layer%s'%nlayer

  with tf.namescope(layername):

  with tf.name_scope("Weights"):

  Weights = tf.Variable(tf.randomnormal([insize,out_size]),name = "Weights")

  tf.summary.histogram(layer_name+"/weights",Weights)

  with tf.name_scope("biases"):

  biases = tf.Variable(tf.zeros([1,out_size]) + 0.1,name = "biases")

  tf.summary.histogram(layer_name+"/biases",biases)

  with tf.namescope("Wxplus_b"):

  Wxplusb = tf.matmul(inputs,Weights) + biases

  #dropout一般加载每个神经层的输出

  Wxplusb = tf.nn.dropout(Wxplusb,keep_prob)

  #看这里看这里,dropout在这里。

  tf.summary.histogram(layername+"/Wxplusb",Wxplus_b)

  if activation_function == None :

  outputs = Wxplusb

  else:

  outputs = activationfunction(Wxplus_b)

  tf.summary.histogram(layer_name+"/outputs",outputs)

  return outputs

  但需要注意的是,神经元的输出层不可以定义dropout参数。因为输出层就是输出的是结果,在输出层定义参数的话,就会导致输出结果被dropout掉。

  例子

  本次例子使用sklearn.datasets,在进行测试的时候,我们只需要改变最下方keep_prob:0.5的值即可,1代表不进行dropout。

  代码

  import tensorflow as tf

  from sklearn.datasets import load_digits

  from sklearn.modelselection import traintest_split

  from sklearn.preprocessing import LabelBinarizer

  digits = load_digits()

  X = digits.data

  y = digits.target

  y = LabelBinarizer().fit_transform(y)

  Xtrain,Xtest,Ytrain,Ytest = traintestsplit(X,y,test_size = 500)

  def addlayer(inputs,insize,outsize,nlayer,activationfunction = None,keepprob = 1):

  layername = 'layer%s'%nlayer

  with tf.namescope(layername):

  with tf.name_scope("Weights"):

  Weights = tf.Variable(tf.randomnormal([insize,out_size]),name = "Weights")

  tf.summary.histogram(layer_name+"/weights",Weights)

  with tf.name_scope("biases"):

  biases = tf.Variable(tf.zeros([1,out_size]) + 0.1,name = "biases")

  tf.summary.histogram(layer_name+"/biases",biases)

  with tf.namescope("Wxplus_b"):

  Wxplusb = tf.matmul(inputs,Weights) + biases

  Wxplusb = tf.nn.dropout(Wxplusb,keep_prob)

  tf.summary.histogram(layername+"/Wxplusb",Wxplus_b)

  if activation_function == None :

  outputs = Wxplusb

  else:

  outputs = activationfunction(Wxplus_b)

  tf.summary.histogram(layer_name+"/outputs",outputs)

  return outputs

  def computeaccuracy(xdata,y_data,prob = 1):

  global prediction

  ypre = sess.run(prediction,feeddict = {xs:xdata,keepprob:prob})

  correctprediction = tf.equal(tf.argmax(ydata,1),tf.argmax(y_pre,1))

  accuracy = tf.reducemean(tf.cast(correctprediction,tf.float32))

  result = sess.run(accuracy,feeddict = {xs:xdata,ys:ydata,keepprob:prob})

  return result

  keep_prob = tf.placeholder(tf.float32)

  xs = tf.placeholder(tf.float32,[None,64])

  ys = tf.placeholder(tf.float32,[None,10])

  l1 = addlayer(xs,64,100,'l1',activationfunction=tf.nn.tanh, keepprob = keepprob)

  l2 = addlayer(l1,100,100,'l2',activationfunction=tf.nn.tanh, keepprob = keepprob)

  prediction = addlayer(l1,100,10,'l3',activationfunction = tf.nn.softmax, keep_prob = 1)

  with tf.name_scope("loss"):

  loss = tf.reducemean(tf.nn.softmaxcrossentropywith_logits(labels=ys,logits = prediction),name = 'loss')

  tf.summary.scalar("loss",loss)

  train = tf.train.AdamOptimizer(0.01).minimize(loss)

  init = tf.initializeallvariables()

  merged = tf.summary.merge_all()

  with tf.Session() as sess:

  sess.run(init)

  train_writer = tf.summary.FileWriter("logs/strain",sess.graph)

  test_writer = tf.summary.FileWriter("logs/test",sess.graph)

  for i in range(5001):

  sess.run(train,feeddict = {xs:Xtrain,ys:Ytrain,keepprob:0.5})

  if i % 500 == 0:无锡妇科医院 http://www.bhnnk120.com/

  print("训练%d次的识别率为:%f。"%((i+1),computeaccuracy(Xtest,Y_test,prob=0.5)))

  trainresult = sess.run(merged,feeddict={xs:Xtrain,ys:Ytrain,keep_prob:0.5})

  testresult = sess.run(merged,feeddict={xs:Xtest,ys:Ytest,keep_prob:0.5})

  trainwriter.addsummary(train_result,i)

  testwriter.addsummary(test_result,i)

  keep_prob = 0.5

  训练结果为:

  训练1次的识别率为:0.086000。

  训练501次的识别率为:0.890000。

  训练1001次的识别率为:0.938000。

  训练1501次的识别率为:0.952000。

  训练2001次的识别率为:0.952000。

  训练2501次的识别率为:0.946000。

  训练3001次的识别率为:0.940000。

  训练3501次的识别率为:0.932000。

  训练4001次的识别率为:0.970000。

  训练4501次的识别率为:0.952000。

  训练5001次的识别率为:0.950000。

  这是keep_prob = 0.5时tensorboard中的loss的图像:

  keep_prob = 1

  训练结果为:

  训练1次的识别率为:0.160000。

  训练501次的识别率为:0.754000。

  训练1001次的识别率为:0.846000。

  训练1501次的识别率为:0.854000。

  训练2001次的识别率为:0.852000。

  训练2501次的识别率为:0.852000。

  训练3001次的识别率为:0.860000。

  训练3501次的识别率为:0.854000。

  训练4001次的识别率为:0.856000。

  训练4501次的识别率为:0.852000。

  训练5001次的识别率为:0.852000。

  这是keep_prob = 1时tensorboard中的loss的图像:

  可以明显看出来keep_prob = 0.5的训练集和测试集的曲线更加贴近。


©著作权归作者所有:来自51CTO博客作者nineteens的原创作品,如需转载,请注明出处,否则将追究法律责任