In TensorFlow 2, you can use tf.backend.eval()
to evaluate a tensor that is outside of a tf.function
if it hasn't yet been evaluated (more on that in the next section).
a, b, c, d, e = tf.unstack(x, axis=1)
print(tf.keras.backend.eval(a))
How is it that is not possible to just type a
and see your tensor value?
You likely not have Eager Execution
enabled. The significance of this delves a bit into the inner workings of TensorFlow.
In TensorFlow there are two modes of execution, Eager Execution
and Graph Execution
.
Eager Execution
In Eager Execution
, operations like tf.unstack
are evaluated immediately and return concrete values. This is the usual behavior you would expect from python and is the default mode of execution in TensorFlow 2 outside of tf.function
and functions like tf.compat.v1.disable_eager_execution()
.
In Eager Execution
, passing a
into the interpreter would indeed return a concrete value.
>>> import tensorflow as tf
>>> # Create a 5x5 matrix
>>> x = tf.constant([[i for i in range(5)] for i in range(5)])
# A bunch of messages regarding compute devices appear as TensorFlow initializes its backend to evaluate the expression immediately
>>> a, b, c, d, e = tf.unstack(x, axis=1)
>>> a
<tf.Tensor: shape=(5,), dtype=int32, numpy=array([0, 0, 0, 0, 0], dtype=int32)>
Graph Execution
With Graph Execution
, every time you input an operation like tf.add(a, b)
or tf.unstack
, these operations are added to a TensorFlow graph rather than being immediately executed. By building the graph first and deferring execution, Tensorflow can improve the performance of the computations by optimizing the built graph.
Because of this, with a statement like a, b, c, d, e = tf.unstack(x, axis=1)
, a
prints the TensorFlow operation rather than an output value.
>>> import tensorflow as tf
>>> # Here we disable eager execution
>>> tf.compat.v1.disable_eager_execution()
>>> # Create a 5x5 matrix as before. Notice the lack of messages
>>> x = tf.constant([[i for i in range(5)] for i in range(5)])
>>> a, b, c, d, e = tf.unstack(x, axis=1)
>>> a
<tf.Tensor 'unstack:0' shape=(5,) dtype=int32>
>>> # Evaluate the graph and store it in result
>>> result = tf.keras.backend.eval(a)
>>> result
array([0, 0, 0, 0, 0], dtype=int32)
>>> # `a` still refers to an operation if you were wondering
>>> a
<tf.Tensor 'unstack:0' shape=(5,) dtype=int32>