程序主要包括:
main.py 主程序
model.py 神经网络模型设置程序
pretreatment.py :数据预处理程序
2、model.py
在该py文件中,主要有一个父类,三个子类,分别对应网络:LSTM、BLSTM、CNNBLSTM
现在对各个部分进行介绍
1)父类
由于篇幅的原因相关的程序代码在git上,大家自行下载对照阅读
从main.py文件通过run()函数进入model.py文件,所以再看代码的时候,找到def run()函数,下面对run()函数中的主要代码进行介绍:
def run(self,train_x,train_y,train_lens,valid_x,valid_y,valid_lens,test_x,test_y,test_lens,FLAGS=None):
self.lr = FLAGS.lr
self.training_iter = FLAGS.train_steps # 迭代的次数,即训练的轮数epoch
self.train_file_path = FLAGS.train_data # 训练语料的路径
self.test_file_path = FLAGS.valid_data # 开发集语料的路径
self.display_step = FLAGS.display_step # 控制运行多少步进行训练情况的显示
pred = self.inference(self.X,self.X_len) # 预测
cost = self.loss(pred) # 评估
传入到函数的参数分别是训练语料、开发集语料、测试语料的字所对应的id、标签以及各个句子的长度(具体的样式见上一篇博客的文章末尾)
pred = self.inference(self.X,self.X_len) ##得出的是预测的标签值,该函数在各个子类中进行实现
cost = self.loss(pred) ##loss的计算,即损失值的计算
损失函数(loss function)是用来估量你模型的预测值f(x)与真实值Y的不一致程度,它是一个非负实值函数,通常使用L(Y, f(x))来表示,损失函数越小,模型的鲁棒性就越好
with tf.name_scope('train'):
global_step = tf.Variable(0,name='tr_global_step',trainable=False)
optimizer = tf.train.AdamOptimizer(learning_rate=self.lr).minimize(cost,global_step=global_step)
tf.name_scope可以让变量有相同的命名
Global_step.name() :train/tr_global_step ???
模型的保存:
with tf.name_scope('saveModel'):
localtime = time.strftime("%X-%Y-%m-%d", time.localtime())
saver = tf.train.Saver()
save_dir = FLAGS.model_dir + localtime + '/'
if not os.path.exists(save_dir):
os.makedirs(save_dir)
在tensorflow中,保存模型和加载模型所用到的类是tf.train.Saver(),在保存好模型之后,一般会出现下面四个文件 :
.meta文件:保存了tensorflow的graph,包括variables、operations、collections等等
checkpoint files:二进制文件,保存了所有weights,biases,gradient and all the other variables的值。也就是上图中的.data-00000-of-00001和.index文件。.data文件包含了所有的训练变量。以前的TensorFlow版本是一个ckpt文件,现在就是这两个文件了。与此同时,Tensorflow还有一个名为checkpoint的文件,只保存最新检查点文件的记录,即最新的保存路径。
import tensorflow as tf
saver = tf.train.Saver()
sess = tf.Session()
saver.save(sess, save_dir, global_step=step) ##保存模型
save_dir:保存路径单位
global_step:给定一个数字,用于保存文件时tensorflow帮你命名,主要是说明了迭代了多少次后保存了
(此处模型保存的介绍来源其他博客)
模型的训练:
with tf.Session() as sess:
max_acc,bestIter = 0.,0
sess.run(tf.global_variables_initializer())
for epoch in xrange(self.training_iter):
for train,num in self.get_batch_data(train_x,train_y,train_lens,self.batch_size,(1-self.drop_rate)):
_,step,trans_matrix,loss,predication = sess.run([optimizer,global_step,self.transition,cost,pred],feed_dict=train)
tags_seqs,_ = self.viterbi_decode(num,predication,train[self.X_len],trans_matrix)
f = self.evaluate(num,tags_seqs,train[self.Y],train[self.X_len])
print 'Iter {}: mini-batch loss={:.6f}, acc={:.6f}'.format(step, loss, f)
save_path = saver.save(sess, save_dir, global_step=step)
print "[+] Model saved in file: %s" % save_path
if epoch%self.display_step == 0:
rd,loss,acc = 0,0.,0.
for valid,num in self.get_batch_data(valid_x,valid_y,valid_lens,self.batch_size):
trans_matrix,_loss,predication = sess.run([self.transition,cost,pred],feed_dict=valid)
loss += _loss
tags_seqs,_ = self.viterbi_decode(num,predication,valid[self.X_len],trans_matrix)
f = self.evaluate(num,tags_seqs,valid[self.Y],valid[self.X_len])
acc += f
rd += 1
loss /= rd
acc /= rd
if acc >max_acc:
max_acc = acc
bestIter = step
print '----------{}----------'.format(time.strftime("%Y-%m-%d %X", time.localtime()))
print 'Iter {}: valid loss(avg)={:.6f}, acc(avg)={:.6f}'.format(step, loss, acc)
print 'round {}: max_acc={} BestIter={}\n'.format(epoch, max_acc, bestIter)
print 'Optimization Finished!'
pred_test_y = []
acc,loss,rd = 0.,0.,0
for test,num in self.get_batch_data(test_x,test_y,test_lens,self.batch_size,shuffle=False):
trans_matrix,_loss,predication = sess.run([self.transition,cost,pred],feed_dict=test)
loss += _loss
rd += 1
tags_seqs,tags_scores = self.viterbi_decode(num,predication,test[self.X_len],trans_matrix)
f = self.evaluate(num,tags_seqs,test[self.Y],test[self.X_len])
acc += f
pred_test_y.extend(tags_seqs)
acc /= rd
loss /= rd
return pred_test_y,loss,acc
训练时显示出的结果如下图所示:
sess.run(tf.global_variables_initializer()) :初始化模型的参数
global_variables_initializer 返回一个用来初始化计算图中所有global variable的op:
函数中调用了variable_initializer()和global_variables()
global_variables()返回一个 Variable list,里面保存的是gloabal variables
variable_initializer()将Variable list中的所有Variable取出来,将其variable.initializer属性做成一个op group
然后看Variable类的源码可以发现,variable.initializer就是一个assign op
所以:
sess.run(tf.global_variables_initializer())就是run了所有global Variable的assign op,这就是初始化参数的本来面目
https://blog.csdn.net/qq_26591517/article/details/80601225
nitialize_all_variables已被弃用,更新成tf.global_variables_initializer
写了init = tf.global_variables_initializer()后不会执行,要在session里加上sess.run(init)后才会执行,否则会有一系列报错
今天暂时写到这里了,后续继续更新