1. 程式人生 > 程式設計 >使用Tensorflow將自己的資料分割成batch訓練例項

使用Tensorflow將自己的資料分割成batch訓練例項

學習神經網路的時候,網上的資料集已經分割成了batch,訓練的時候直接使用batch.next()就可以獲取batch,但是有的時候需要使用自己的資料集,然而自己的資料集不是batch形式,就需要將其轉換為batch形式,本文將介紹一個將資料打包成batch的方法。

一、tf.slice_input_producer()

首先需要講解兩個函式,第一個函式是 :tf.slice_input_producer(),這個函式的作用是從輸入的tensor_list按要求抽取一個tensor放入檔名佇列,下面解釋下各個引數:

tf.slice_input_producer(tensor_list,num_epochs=None,shuffle=True,seed=None,capacity=32,shared_name=None,name=None)

tensor_list 這個就是輸入,格式為tensor的列表;一般為[data,label],即由特徵和標籤組成的資料集

num_epochs 這個是你抽取batch的次數,如果沒有給定值,那麼將會抽取無數次batch(這會導致你訓練過程停不下來),如果給定值,那麼在到達次數之後就會報OutOfRange的錯誤

shuffle 是否隨機打亂,如果為False,batch是按順序抽取;如果為True,batch是隨機抽取

seed 隨機種子

capcity 佇列容量的大小,為整數

name 名稱

舉個例子:我的data的shape為(4000,10),label的shape為(4000,2),執行下面這行程式碼

input_queue = tf.train.slice_input_producer([data,label],num_epochs=1,capacity=32 )

結果如圖,可以看出返回值為一個包含兩組資料的list,每個list的shape與輸入的data和label的shape對應

二、tf.train.batch()& tf.train.shuffle_batch()

第二個函式為:tf.train.batch(),tf.train.shuffle_batch(),這個函式的作用為生成大小為batch_size的tensor,下面解釋下各個引數:

tf.train.batch([data,batch_size=batch_size,capacity=capacity,num_threads=num_thread,allow_smaller_final_batch= True)
tf.train.shuffle_batch([example,allow_smaller_final_batch=True)

[data,label] 輸入的樣本和標籤

batch_size batch的大小

capcity 佇列的容量

num_threads 執行緒數,使用多少個執行緒來控制整個佇列

allow_smaller_final_batch 這個是當最後的幾個樣本不夠組成一個batch的時候用的引數,如果為True則會重新組成一個batch

下面給出生成batch的函式,由上面兩個函式組成:

def get_Batch(data,label,batch_size):
 print(data.shape,label.shape)
 input_queue = tf.train.slice_input_producer([data,capacity=32 ) 
 x_batch,y_batch = tf.train.batch(input_queue,num_threads=1,allow_smaller_final_batch=False)
 return x_batch,y_batch

還是同樣的輸入,batch_size設為2000,看下執行後的返回值的shape:

可以發現,返回是樣本數目為2000的tensor,也就是達到了將自己的資料打包成batch的功能

三、batch的使用方法

生成batch只完成了一半,後面的使用方法也比較複雜,直接上一個完整的程式來講解會方便理解一些:下面程式碼構建了一個單層感知機,對資料進行分類,主要看一下訓練過程中如何使用生成好了的batch,具體細節都寫在註釋裡面了。

import tensorflow as tf
import scipy.io as sio
import numpy as np
 
 
def get_Batch(data,y_batch
 
 
data = sio.loadmat('data.mat')
train_x = data['train_x']
train_y = data['train_y']
test_x = data['test_x']
test_y = data['test_y']
 
x = tf.placeholder(tf.float32,[None,10])
y = tf.placeholder(tf.float32,2])
 
w = tf.Variable(tf.truncated_normal([10,2],stddev=0.1))
b = tf.Variable(tf.truncated_normal([2],stddev=0.1))
pred = tf.nn.softmax(tf.matmul(x,w) + b)
 
loss = tf.reduce_mean(-tf.reduce_sum(y * tf.log(pred),reduction_indices=[1]))
optimizer = tf.train.AdamOptimizer(2e-5).minimize(loss)
correct_prediction = tf.equal(tf.argmax(y,1),tf.argmax(pred,1))
accuracy = tf.reduce_mean(tf.cast(correct_prediction,tf.float32),name='evaluation')
 
x_batch,y_batch = get_Batch(train_x,train_y,1000)
# 訓練
with tf.Session() as sess:
 #初始化引數
 sess.run(tf.global_variables_initializer())
 sess.run(tf.local_variables_initializer())
 # 開啟協調器
 coord = tf.train.Coordinator()
 # 使用start_queue_runners 啟動佇列填充
 threads = tf.train.start_queue_runners(sess,coord)
 epoch = 0
 try:
  while not coord.should_stop():
   # 獲取訓練用的每一個batch中batch_size個樣本和標籤
   data,label = sess.run([x_batch,y_batch])
   sess.run(optimizer,feed_dict={x: data,y: label})
   train_accuracy = accuracy.eval({x: data,y: label})
   test_accuracy = accuracy.eval({x: test_x,y: test_y})
   print("Epoch %d,Training accuracy %g,Testing accuracy %g" % (epoch,train_accuracy,test_accuracy))
   epoch = epoch + 1
 except tf.errors.OutOfRangeError: # num_epochs 次數用完會丟擲此異常
  print("---Train end---")
 finally:
  # 協調器coord發出所有執行緒終止訊號
  coord.request_stop()
  print('---Programm end---')
 coord.join(threads) # 把開啟的執行緒加入主執行緒,等待threads結束

總共訓練的次數為(樣本數目/batch_size)*num_epochs

四、 簡單生成Batch的方法

最近發現了一種簡單生生成batch的方法,實現簡單,操作方便,就是時間複雜度可能高了一點,直接上程式碼。通過np.random.choice方法每次在範圍[0,len(all_data))內抽取大小為size的索引。然後通過這部分索引構建batch。

epoch = 150
for i in tqdm(range(epoch)):
 # 在total_train_xs,total_train_ys資料集中隨機抽取batch_size個樣本出來
 # 作為本輪迭代的訓練資料batch_xs,batch_ys
 batch_size = 1000
 sample_idxs = np.random.choice(range(len(all_data)),size=batch_size)
 batch_xs = []
 batch_ys = []
 
 val_sample_idxs = np.random.choice(range(len(all_data)),size=batch_size)
 val_batch_xs = []
 val_batch_ys = []
 
 for j in range(batch_size):
  train_id = sample_idxs[j]
  batch_xs.append(all_data[train_id])
  batch_ys.append(all_label[train_id])
 
  val_id = val_sample_idxs[j]
  val_batch_xs.append(all_data[val_id])
  val_batch_ys.append(all_label[val_id])
 
 batch_xs = np.array(batch_xs)
 batch_ys = np.array(batch_ys)
 val_batch_xs = np.array(val_batch_xs)
 val_batch_ys = np.array(val_batch_ys)
 
 
 # 喂訓練資料進去訓練
 sess.run(train_step,feed_dict={x: batch_xs,y_: batch_ys})
 if i % 50 == 0:
  y_train_pred = np.array(sess.run(y,feed_dict={x: batch_xs})).reshape(len(batch_xs))
  y_pred = np.array(sess.run(y,feed_dict={x: val_batch_xs})).reshape(len(val_batch_xs))
  # draw(y_test,y_pred)
  print("Iteration %d,train RMSE %f,val RMSE %f" % (i,calcaulateRMSE(batch_ys,y_train_pred),calcaulateRMSE(val_batch_ys,y_pred)))

以上這篇使用Tensorflow將自己的資料分割成batch訓練例項就是小編分享給大家的全部內容了,希望能給大家一個參考,也希望大家多多支援我們。