¿Cómo asignar un valor a una variable de TensorFlow?


79

Estoy tratando de asignar un nuevo valor a una variable tensorflow en Python.

import tensorflow as tf
import numpy as np

x = tf.Variable(0)
init = tf.initialize_all_variables()
sess = tf.InteractiveSession()
sess.run(init)

print(x.eval())

x.assign(1)
print(x.eval())

Pero el resultado que obtengo es

0
0

Entonces el valor no ha cambiado. ¿Qué me estoy perdiendo?

Respuestas:


124

En TF1, la declaración x.assign(1)en realidad no asignar el valor 1a x, sino que crea una tf.Operationque tiene que explícitamente ejecutar para actualizar la variable * Una llamada al. Operation.run(), O Session.run()puede ser utilizado para ejecutar la operación:

assign_op = x.assign(1)
sess.run(assign_op)  # or `assign_op.op.run()`
print(x.eval())
# ==> 1

(* De hecho, devuelve un tf.Tensor, correspondiente al valor actualizado de la variable, para facilitar la cadena de asignaciones).

Sin embargo, en TF2 x.assign(1)ahora asignará el valor con entusiasmo:

x.assign(1)
print(x.numpy())
# ==> 1

¡Gracias! assign_op.run () da un error: AttributeError: El objeto 'Tensor' no tiene el atributo 'ejecutar'. Pero sess.run (assign_op) funciona perfectamente bien.
— abora

En este ejemplo, ¿se sobrescriben los datos Variable xalmacenados en la memoria antes de assignejecutar la operación / tensor mutable o se crea un nuevo tensor que almacena el valor actualizado?
— dannygoldstein

3
La implementación actual de assign()sobrescribe el valor existente.
— mrry

1
¿Hay alguna forma de asignar un nuevo valor a a Variablesin crear operaciones adicionales en el gráfico? Parece que cada variable ya tiene una operación Asignar creada para ella, pero llamando my_var.assign()o tf.assign()crea una nueva operación en lugar de usar la existente.
— Nathan

No creo que esto sea relevante aquí, pero puedes darle a assignun parámetro tensorial como una operación matemática. Y de esta manera crear un contador que se actualiza cada vez que se evalúa la operación de asignación: op = t.assign(tf.add(t, 1)).
— Eliel Van Hojman

40

También puede asignar un nuevo valor a una tf.Variablesin la adición de una operación a la gráfica: tf.Variable.load(value, session). Esta función también puede ahorrarle agregar marcadores de posición al asignar un valor desde fuera del gráfico y es útil en caso de que el gráfico esté finalizado.

import tensorflow as tf
x = tf.Variable(0)
sess = tf.Session()
sess.run(tf.global_variables_initializer())
print(sess.run(x))  # Prints 0.
x.load(1, sess)
print(sess.run(x))  # Prints 1.

Actualización: esto está descatalogado en TF2 ya que la ejecución ávida es predeterminada y los gráficos ya no están expuestos en la API de cara al usuario .


2
Advertencia: no puede cargarlo con una matriz que tenga una forma diferente a la forma del valor inicial de la variable.
— Rajarshee Mitra

1
Variable.load (de tensorflow.python.ops.variables) está obsoleto y se eliminará en una versión futura. Instrucciones para la actualización: Prefiera Variable.assign que tiene un comportamiento equivalente en 2.X. No estoy seguro de cómo cambiar los valores de una variable en Tensorflow 2.0 sin agregar una operación al gráfico
— João Abrantes

15

En primer lugar, puede asignar valores a variables / constantes simplemente introduciendo valores en ellas de la misma manera que lo hace con los marcadores de posición. Entonces esto es perfectamente legal de hacer:

import tensorflow as tf
x = tf.Variable(0)
with tf.Session() as sess:
    sess.run(tf.global_variables_initializer())
    print sess.run(x, feed_dict={x: 3})

Con respecto a su confusión con el operador tf.assign () . En TF no se ejecuta nada antes de ejecutarlo dentro de la sesión. Así que siempre tienes que hacer algo como esto: op_name = tf.some_function_that_create_op(params)y luego, dentro de la sesión, ejecutas sess.run(op_name). Usando asignar como ejemplo, hará algo como esto:

import tensorflow as tf
x = tf.Variable(0)
y = tf.assign(x, 1)
with tf.Session() as sess:
    sess.run(tf.global_variables_initializer())
    print sess.run(x)
    print sess.run(y)
    print sess.run(x)

@RobinDinse, lo hace. En el ejemplo anterior, obtienes 0,1,1 como tu salida estándar.
— Rajarshee Mitra

4
Tenga en cuenta que introducir el valor a través de feed_dictno asigna permanentemente ese valor a la variable, sino solo para esa llamada de ejecución en particular.
— Robin Dinse

@RobinDinse ¿cómo puedo asignar ese valor de forma permanente? Si puede, vea mi pregunta aquí stackoverflow.com/questions/53141762/…
— volperossa

3

Además, debe tenerse en cuenta que si está utilizando your_tensor.assign(), tf.global_variables_initializerno es necesario que se llame explícitamente ya que la operación de asignación lo hace por usted en segundo plano.

Ejemplo:

In [212]: w = tf.Variable(12)
In [213]: w_new = w.assign(34)

In [214]: with tf.Session() as sess:
     ...:     sess.run(w_new)
     ...:     print(w_new.eval())

# output
34 

Sin embargo, esto no inicializará todas las variables, sino que solo inicializará la variable en la que assignse ejecutó.


1

Respondí una pregunta similar aquí . Busqué en muchos lugares que siempre creaban el mismo problema. Básicamente, no quería asignar un valor a los pesos, sino simplemente cambiar los pesos. La versión corta de la respuesta anterior es:

tf.keras.backend.set_value(tf_var, numpy_weights)


0

Aquí está el ejemplo de trabajo completo:

import numpy as np
import tensorflow as tf

w= tf.Variable(0, dtype=tf.float32) #good practice to set the type of the variable
cost = 10 + 5*w + w*w
train = tf.train.GradientDescentOptimizer(0.01).minimize(cost)

init = tf.global_variables_initializer()
session = tf.Session()
session.run(init)

print(session.run(w))

session.run(train)
print(session.run(w)) # runs one step of gradient descent

for i in range(10000):
  session.run(train)

print(session.run(w))

Tenga en cuenta que la salida será:

0.0
-0.049999997
-2.499994

Esto significa que al principio la Variable era 0, como se definió, luego, después de un solo paso de degradado decente, la variable era -0.049999997, y después de 10.000 pasos más, llegamos a -2.499994 (según nuestra función de costo).

Nota: originalmente utilizó la sesión interactiva. La sesión interactiva es útil cuando es necesario ejecutar varias sesiones diferentes en el mismo script. Sin embargo, usé la sesión no interactiva para simplificar.


0

Use el modo de ejecución ansioso de Tensorflow, que es el más reciente.

import tensorflow as tf
tf.enable_eager_execution()
my_int_variable = tf.get_variable("my_int_variable", [1, 2, 3])
print(my_int_variable)

-1

Así que tuve un caso diferente en el que necesitaba asignar valores antes de ejecutar una sesión, así que esta era la forma más fácil de hacerlo:

other_variable = tf.get_variable("other_variable", dtype=tf.int32,
  initializer=tf.constant([23, 42]))

aquí estoy creando una variable y asignándole valores al mismo tiempo


-10

Hay un enfoque más sencillo:

x = tf.Variable(0)
x = x + 1
print x.eval()

3
la operación estaba examinando el uso de tf.assign, no la adición.
— vega
Al usar nuestro sitio, usted reconoce que ha leído y comprende nuestra Política de Cookies y Política de Privacidad.
Licensed under cc by-sa 3.0 with attribution required.