Tensorflow學習筆記:變數作用域、模型的載入與儲存、執行緒與佇列實現多執行緒讀取樣本
# tensorflow變數作用域
用上下文語句規定作用域
with tf.variable_scope("作用域_name")
......
這樣可以使得變數在tensorboard中的顯示更加簡介
# 增加變數顯示
1、用tf.summary.scalar(name="",tensor) 收集單個值(0維的值)
用tf.summary.histogram(name="",tensor) 收集高維度的值
2、合併變數並寫入event檔案
merged = tf.summary.merge_all()
summary = sess.run(merged) #每次迭代都需要執行
FileWriter.add_summary(summary,i) #i代表第幾次的值
#模型的儲存與載入
儲存為checkpoint檔案
tf.train.Saver(var_list=None, #用字典或列表傳遞要儲存和還原的變數
max_to_keep #保留最近的幾個檔案的最大數目
)
返回一個例項saver
saver.save(sess,'path+name')
saver.restore(sess,'path+name')
示例:
saver = tf.train.Saver(var_list=(w,b),max_to_keep = 3)
with tf.Session() as sess:
saver.save(sess,'./train_data/model')
Saver不是op,不用run
如果需要載入模型,在訓練開始之前進行載入
if os.path.exists("checkpoint") #判斷儲存時建立的checkpoint是否存在
saver.restore(sess,'./trained_data/model')
#執行緒佇列與IO操作
#佇列
tf.FIFOQueue()佇列,先進先出
tf.RandomShuffleQueue()隨機出佇列
#主要用到FIFOQueue
FIFOQueue(capacity, #最大數量
dtype, #資料型別
name = None)
方法:
dequeue()出佇列
enqueue(vals)進佇列
enqueue_many(vals) #vals為包含多組資料的列表或元組
size() 返回大小
#佇列管理器(可以建立執行緒)
tf.train.QueueRunner(queue,enqueue_ops = None)
其中queue是列表物件例項,en queue_ops = [enqueue_op,dequque_op,...],指定執行緒做什麼操作,[]*2代表指定兩個執行緒
create_threads(sess,
coord=None #執行緒協調器,後面再說
start=False #為True直接啟動執行緒,為False必須呼叫start()來啟動
) #執行執行緒進行操作
返回一個執行緒的例項
示例:
#佇列中加入數,每次取出後加1放入佇列
import tensorflow as tf
import os
#定義佇列
Q = tf.FIFOQueue(100,tf.float32)
#定義變數
var = tf.Variable(0.0,dtype = tf.float32)
#取出變數自增後放入佇列
data = tf.assign_add(var,tf.constant(1.0))
#data放入佇列Q
enq_op = Q.enqueue(data)
Q_thread_op = tf.train.QueueRunner(Q,enqueue_ops = [enq_op])
init_op = tf.global_variables_initializer()
with tf.Session() as sess:
sess.run(init_op)
threads = Q_thread_op.create_threads(sess, start = True)
for i in range(300):
print(sess.run(Q.dequeue()),Q.size().eval())
#執行緒協調器tf.train.Coordinator()
示例:加入執行緒協調器
import tensorflow as tf
import os
#定義佇列
Q = tf.FIFOQueue(100,tf.float32)
#定義變數
var = tf.Variable(0.0,dtype = tf.float32)
#取出變數自增後放入佇列
data = tf.assign_add(var,tf.constant(1.0))
#data放入佇列Q
enq_op = Q.enqueue(data)
Q_thread_op = tf.train.QueueRunner(Q,enqueue_ops = [enq_op])
init_op = tf.global_variables_initializer()
with tf.Session() as sess:
sess.run(init_op)
coord = tf.train.Coordinator() #建立執行緒協調器
threads = Q_thread_op.create_threads(sess,coord = coord, start = True) #用執行緒協調器開啟執行緒
for i in range(300):
print(sess.run(Q.dequeue()),Q.size().eval())
coord.request_stop() #請求執行緒結束
coord.join(threads) #回收執行緒
#檔案讀取
1、構造檔案讀取佇列
tf.train.string_input_producer(string_tensor, num_epochs=None, shuffle=True, capacity=32)
string_tensor:一維字串張量,儲存要讀取的樣本檔案的字串
num_epochs:讀取迴圈次數,預設無限次
shuffle:隨機選擇檔案讀取
capacity:檔案讀取佇列的容量
2、檔案閱讀器------讀取佇列內容
tf.TextLineReader
閱讀文字檔案(.txt,.CSV等)格式,預設按行讀取
return:讀取器例項
tf.FixedLengthRecordReader(record_bytes)
閱讀二進位制檔案,引數為要讀取的位元組數
return 讀取器例項
tf.TFRecordReader()(後面再說)
閱讀器都有一個共同的方法:read(file_queue)
return :一個張量,(檔名字,value讀取的內容(行,位元組))
3、檔案內容解碼器
tf.decode_csv( records, #即上面的value
record_defaults = None #所返回張量的型別
field_delim = None #預設分隔符
name = None)
tf.decode_raw(bytes,out_type,little_endian = None)
讀取二進位制檔案
#批處理:在解碼器解碼之後進行,系統將執行多遍讀取操作
read_result_batch = tf.train.batch(read_result, #解碼器的解碼結果
batch_size = 5, #每個batch的數量,該大小跟佇列大小,資料個數無關,一般資料可以迴圈讀取,如果batch_size很大,則會重複取
num_threads = 1,#利用多少個執行緒處理
capacity = 5) #佇列的大小,沒有關係,只是定義佇列的大小
#例項:讀取CSV檔案
1、找到檔案構造樣本檔案的目錄+檔名
2、構造檔案佇列
3、構造閱讀器,讀取檔案(一行)
4、構造解碼器,解碼內容
5、批處理
def csvread(filelist):
#1、構造檔案字串列表
file_queue = tf.train.string_input_producer(filelist)
#2、構造閱讀器讀取資料
reader = tf.TextLineReader()
key, value = reader.read(file_queue)
#3、構造解碼器進行解碼
recoders = [[1],[1]]
read_result = tf.decode_csv(value, record_defaults = recoders)
#4、批量讀取
read_result_batch = tf.train.batch(read_result, batch_size = 5, num_threads = 1, capacity = 7)
return read_result_batch
import tensorflow as tf
import os
if __name__ == "__main__":
#用os模組查詢存放資料檔案的目錄下是否真的存在資料檔案
dir_file_list = os.listdir("C:\\Users\\xie\\csv_data")
#構造資料檔案路徑+檔名的字串列表
for i in range(len(dir_file_list)):
dir_file_list[i] = "C:\\Users\\xie\\csv_data\\" + dir_file_list[i]
#呼叫函式獲得樣本batch
result_batch = csvread(dir_file_list)
with tf.Session() as sess:
#定義執行緒管理器
coord = tf.train.Coordinator()
#用tf.train.start_queue_runners方法開啟queue的子執行緒檔案讀取,其機制是:
#所有關於queue讀取的操作都被放在一個集合內部,當呼叫該函式時,所有的讀取子程序啟動,進行讀取
thread = tf.train.start_queue_runners(sess, coord = coord)
print(sess.run(result_batch))
coord.request_stop()
coord.join(thread)