TF.VARIABLE、TF.GET_VARIABLE、TF.VARIABLE_SCOPE以及TF.NAME_SCOPE關係

1. tf.Variable與tf.get_variable

tensorflow提供了經過變量名稱來建立或者獲取一個變量的機制。經過這個機制,在不一樣的函數中能夠直接經過變量的名字來使用變量,而不須要將變量經過參數的形式處處傳遞。 
TensorFlow中經過變量名獲取變量的機制主要是經過tf.get_variable和tf.variable_scope實現的。 
固然,變量也能夠經過tf.Varivale來建立。當tf.get_variable用於變量建立時,和tf.Variable的功能基本等價python

1
2
3
#如下兩個定義是等價的
=  tf.get_variable( 'v' , shape = [ 1 ], initializer = tf.constant_initializer( 1.0 ))
=  tf.Variable(tf.constant( 1.0 , shape = [ 1 ], name = 'v' )

tf.get_varialbe和tf.Variable最大的區別在於:tf.Variable的變量名是一個可選項,經過name=’v’的形式給出。可是tf.get_variable必須指定變量名函數

2. tf.get_variable與tf.variable_scope

上面已經提到過了:TensorFlow中經過變量名獲取變量的機制主要是經過tf.get_variable和tf.variable_scope實現的。在這裏,我主要解釋下你們深惡痛絕的reuse問題。 
其實只要記住一件事情就ok了:當reuse爲False或者None時(這也是默認值),同一個tf.variable_scope下面的變量名不能相同;當reuse爲True時,tf.variable_scope只能獲取已經建立過的變量。 
下面咱們經過代碼來看下:spa

1
2
3
4
5
6
#reuse=False時會報錯的狀況:
with tf.variable_scope( 'foo' ):
     =  tf.get_variable( 'v' ,[ 1 ],initializer = tf.constant_initializer( 1.0 ))
 
with tf.variable_scope( 'foo' ):
     v1  =  tf.get_variable( 'v' ,[ 1 ])

在這種狀況下會報錯:Variable foo/v already exists, disallowed.Did you mean to set reuse=True in Varscope? 
其緣由就是在命名空間foo中建立了相同的變量。若是我要在foo下建立一個變量v1,其name=‘v’,只須要將reuse設置爲Ture就ok了。將上面第二部分代碼修改成:code

1
2
3
with tf.variable_scope( 'foo' , reuse = True ):
     v1  =  tf.get_variable( 'v' ,[ 1 ])
     print (v1.name)       #結果爲foo/v

當reuse已經設置爲True時,tf.variable_scope只能獲取已經建立過的變量。這個時候,在命名空間bar中建立name=‘v’的變量v3,將會報錯:Variable bar/v dose not exists, diallowed. Did you mean to set reuse=None in VarScope?blog

1
2
with tf.variable_scope( 'bar' , reuse = True ):
     v3  =  tf.get_variable( 'v' ,[ 1 ])

簡而言之,reuse=False時,tf.variable_scope建立變量;reuse=True時,tf.variable_scope獲取變量ci

3. tf.variable_scope與tf.name_scope

除了tf.variable_scope,tf.name_scope函數也提供了命名空間管理的功能。這兩個函數在大部分狀況下是等價的,惟一的區別是在使用tf.get_variable函數時。 
tf.get_variable函數不受tf.name_scope的影響。 
咱們從代碼看下這句話的具體意思。 
首先是tf.variable_scope:get

1
2
3
with tf.variable_scope( 'foo' ):
     =  tf.get_variable( 'bar' ,[ 1 ])
     print (a.name) #結果爲foo/bar:0

  

再看tf.name_scope:string

1
2
3
4
5
6
with tf.name_scope( 'a' ):
     a = tf.Variable([ 1 ])
     print (a.name) #結果爲a/Variable:0
 
     b = tf.get_variable( 'b' ,[ 1 ])
     print (b.name) #結果爲b:0

  

 

從這個結果中,咱們能很清晰地看到,tf.get_variable建立的變量並非a/b:0,而是b:0。這就表示了在tf.name_scope函數下,tf.get_variable不受其約束it

相關文章
相關標籤/搜索