【TensorFlow-windows】name_scope与variable_scope
前言
探索一下variable_scope和name_scope相關的作用域,為下一章節tensorboard的學習做準備
其實關于variable_scope與get_variable實現變量共享,在最開始的博客有介紹過:
【TensorFlow-windows】學習筆記二——低級API
當然還是國際慣例,參考博客:
tensorflow: name_scope 和 variable_scope區別及理解
tensorflow學習筆記(十七):name&variable scope
tensorflow官方文檔name_scope
tensorflow官方文檔get_varialbe
tensorflow官方文檔variable_scope
variable_scope相關
先引入對應包:
import tensorflow as tf import numpy as npVariable定義的變量是否共享
a1 = tf.Variable(1,name='aaa') a2 = tf.Variable(2,name='aaa') init=tf.initialize_all_variables() with tf.Session() as sess:sess.run(init)print(a1.eval())#1print(a2.eval())#2 print(a1) #<tf.Variable 'aaa:0' shape=() dtype=int32_ref> print(a2) #<tf.Variable 'aaa_1:0' shape=() dtype=int32_ref>結論:Variable定義的權重不共享,會自動給變量按照定義順序加后綴_索引,比如第2此定義的aaa得到的名字是aaa_1,所以他們是完全不同的兩個變量,名稱也不同。
Variable定義與get_variable定義有什么區別
#variable創建方式 tf.Variable(<initial-value>, name=<optional-name>) #get_variable創建方式 tf.get_variable(name,shape=None,dtype=None,initializer=None,regularizer=None,trainable=True,collections=None,caching_device=None,partitioner=None,validate_shape=True,use_resource=None,custom_getter=None,constraint=None )結論:Variable定義不實現共享,所以只需要初始值就行了,名字無所謂。get_variable要通過名字實現共享,所以必須給變量一個名字,其余無所謂。
直接定義兩個同名的get_variable變量
b1 = tf.get_variable(name='b',initializer=10) init = tf.initialize_all_variables() with tf.Session() as sess:sess.run(init)print(b1.eval())#10 b2 = tf.get_variable(name='b',initializer=20) ''' Variable b already exists, disallowed. Did you mean to set reuse=True or reuse=tf.AUTO_REUSE in VarScope? Originally defined at: '''結論:不能直接定義兩個同名get_variable變量,必須通過特定方法實現共享
第一種共享方法
在variable_scope內部使用reuse_variables函數:
with tf.variable_scope('dd') as scope:d1=tf.get_variable(name='d',initializer=10.0,dtype=tf.float32)scope.reuse_variables()d2=tf.get_variable(name='d',initializer=20.0,dtype=tf.float32)上述在同一個變量空間中,定義兩個同名變量,通過reuse_variable實現共享,輸出結果如下:
print(d1,d2) init=tf.initialize_all_variables() with tf.Session() as sess:sess.run(init)print(d1.eval(),d2.eval()) ''' <tf.Variable 'dd/d:0' shape=() dtype=float32_ref> <tf.Variable 'dd/d:0' shape=() dtype=float32_ref> 10.0 10.0 '''結論:可以通過reuse_variable實現共享,但是第二次初始化的值是無法覆蓋第一次初始化的值的
第二種共享方法
在使用variable_scope建立變量空間的時候,如果是復用一個已定義的變量空間中的變量,直接將reuse設置為True
with tf.variable_scope('ff') as scope:f1=tf.get_variable(name='f',initializer=10.0,dtype=tf.float32) with tf.variable_scope('ff',reuse=True) as scope:f2=tf.get_variable(name='f',initializer=20.0,dtype=tf.float32) with tf.variable_scope('gg') as scope:g=tf.get_variable(name='f',initializer=20.0,dtype=tf.float32)輸出看看
print(f1,f2,g) init=tf.initialize_all_variables() with tf.Session() as sess:sess.run(init)print(f1.eval(),f2.eval(),g.eval()) ''' <tf.Variable 'ff/f:0' shape=() dtype=float32_ref> <tf.Variable 'ff/f:0' shape=() dtype=float32_ref> <tf.Variable 'gg/f:0' shape=() dtype=float32_ref> 10.0 10.0 20.0 '''結論:可以通過函數參數reuse實現變量共享
不同變量空間中的相同名稱變量是否共享
結論:無法共享,比如上例中f1和g無法共享,雖然名稱都是f,但是所在變量空間不同。
第三種共享方法
調用函數的時候,自動檢測是否需要reuse
with tf.variable_scope('ee',reuse=tf.AUTO_REUSE) as scope:e2=tf.get_variable(name='e',initializer=10.0,dtype=tf.float32)e3=tf.get_variable(name='e',initializer=20.0,dtype=tf.float32) with tf.variable_scope('ee',reuse=tf.AUTO_REUSE) as scope:e4=tf.get_variable(name='e',initializer=30.0,dtype=tf.float32) init = tf.initialize_all_variables() with tf.Session() as sess:sess.run(init)print(e2,e3,e4)print(e2.eval(),e3.eval(),e4.eval()) ''' <tf.Variable 'ee/e:0' shape=() dtype=float32_ref> <tf.Variable 'ee/e:0' shape=() dtype=float32_ref> <tf.Variable 'ee/e:0' shape=() dtype=float32_ref> 10.0 10.0 10.0 '''如果之前沒創建過共享變量,不適用自動檢測,而直接reuse會報錯
with tf.variable_scope('ee',reuse=True) as scope:e2=tf.get_variable(name='e',initializer=10.0,dtype=tf.float32) '''Variable ee/e does not exist, or was not created with tf.get_variable(). Did you mean to set reuse=tf.AUTO_REUSE in VarScope? '''結論:如果不確定之前是否創建過共享變量,最好是使用AUTO_REUSE自動檢測
name_scope相關
直接用namescope是否能隔絕共享變量
with tf.name_scope('f') as nscope:f1 = tf.get_variable('f',initializer=10.0,dtype=tf.float32) with tf.name_scope('g') as nscope:g = tf.get_variable('f',initializer=20.0,dtype=tf.float32) ''' Variable f already exists, disallowed. Did you mean to set reuse=True or reuse=tf.AUTO_REUSE in VarScope? Originally defined at: '''結論:無法直接用name_scope隔絕共享變量
在不同namesope中是否可以共享變量
創建兩個命名空間,但是兩個命名空間包含相同的變量空間,設置共享變量h
with tf.name_scope('test1') as scope:with tf.variable_scope('h',reuse=tf.AUTO_REUSE):h1 = tf.get_variable('hh',initializer=10.0,dtype=tf.float32) with tf.name_scope('test2') as scope:with tf.variable_scope('h',reuse=tf.AUTO_REUSE):h2 = tf.get_variable('hh',initializer=10.0,dtype=tf.float32)測試是否能實現變量共享
init = tf.initialize_all_variables() with tf.Session() as sess:sess.run(init)print(h1,h2)print(h1.eval(),h2.eval())op=tf.assign(h1,30.0)sess.run(op)print(h1.eval(),h2.eval()) ''' <tf.Variable 'h/hh:0' shape=() dtype=float32_ref> <tf.Variable 'h/hh:0' shape=() dtype=float32_ref> 10.0 10.0 30.0 30.0 '''結論:命名空間不能控制是否共享,但是變量空間可以控制變量共享。
總結
get_variable與variable_scope配合可以實現變量共享。
name_scope無法實現變量共享,但是如果看過之前的博客可以發現,它的一個作用是將一系列操作封裝在一起,這樣畫圖的時候網絡結構比較清晰。
其它作用以后遇到再補充,主要是為了下一章節學習tensorboard做準備。
總結
以上是生活随笔為你收集整理的【TensorFlow-windows】name_scope与variable_scope的全部內容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: 碧蓝航线练级攻略 快速练船攻略
- 下一篇: 小小军团英雄装备搭配与心得