def _testDuplicateTensorArrayFails(self, use_gpu): with self.test_session(use_gpu=use_gpu) as sess: h1 = gen_data_flow_ops._tensor_array( size=1, dtype=tf.float32, tensor_array_name="foo") c1 = gen_data_flow_ops._tensor_array_write(h1, 0, 4.0) h2 = gen_data_flow_ops._tensor_array( size=1, dtype=tf.float32, tensor_array_name="foo") c2 = gen_data_flow_ops._tensor_array_write(h2, 0, 5.0) with self.assertRaises(errors.AlreadyExistsError): sess.run([c1, c2])
def _testTensorArrayReadWrongIndexOrDataTypeFails(self, use_gpu): with self.test_session(use_gpu=use_gpu): h = gen_data_flow_ops._tensor_array( dtype=tf.float32, tensor_array_name="foo", size=3) with tf.control_dependencies([ gen_data_flow_ops._tensor_array_write(h, 0, [[4.0, 5.0]])]): # Test reading wrong datatype r0_bad = gen_data_flow_ops._tensor_array_read(h, 0, tf.int64) with self.assertRaisesOpError( "TensorArray dtype is float but Op requested dtype int64."): r0_bad.eval() # Test reading from a different index than the one we wrote to r1 = gen_data_flow_ops._tensor_array_read(h, 1, tf.float32) with self.assertRaisesOpError( "Could not read from TensorArray index 1 because " "it has not yet been written to."): r1.eval() # Test reading from a negative index with self.assertRaisesOpError( "Tried to read from index -1 but array size is: 3"): gen_data_flow_ops._tensor_array_read(h, -1, tf.float32).eval() # Test reading from too large an index with self.assertRaisesOpError( "Tried to read from index 3 but array size is: 3"): gen_data_flow_ops._tensor_array_read(h, 3, tf.float32).eval()
def __init__( self, dtype, size, tensor_array_name=None, handle=None, name=None): """Construct a new TensorArray or wrap an existing TensorArray handle. Args: dtype: (required) data type of the TensorArray. size: (required) int32 scalar `Tensor`: the size of the TensorArray. tensor_array_name: (optional) Python string: the name of the TensorArray. This is used when creating the TensorArray handle. If this value is set, handle should be None. handle: (optional) A `Tensor` handle to an existing TensorArray. If this is set, tensor_array_name should be None. name: A name for the operation (optional). Raises: ValueError: if both handle and tensor_array_name are provided. """ if handle and tensor_array_name: raise ValueError( "Cannot construct with both handle and tensor_array_name") with ops.op_scope([handle, size], name, "TensorArray") as scope: if handle: self._handle = handle else: self._handle = gen_data_flow_ops._tensor_array( dtype=dtype, size=size, tensor_array_name=tensor_array_name, name=scope) self._flow = constant_op.constant(0, dtype=_dtypes.float32) self._dtype = dtype self._gradient_add = False
def _testTensorGradArrayWriteRead(self, use_gpu): with self.test_session(use_gpu=use_gpu) as sess: h = gen_data_flow_ops._tensor_array( dtype=tf.float32, tensor_array_name="foo", size=3) g_h = gen_data_flow_ops._tensor_array_grad(h) writes = [ gen_data_flow_ops._tensor_array_write(h, 0, [[4.0, 5.0]]), gen_data_flow_ops._tensor_array_write(h, 1, [[1.0]]), gen_data_flow_ops._tensor_array_write(h, 2, -3.0)] grad_writes = [ gen_data_flow_ops._tensor_array_write(g_h, 0, [[5.0, 6.0]]), gen_data_flow_ops._tensor_array_write(g_h, 1, [[2.0]]), gen_data_flow_ops._tensor_array_write(g_h, 2, -2.0)] with tf.control_dependencies(writes): r0 = gen_data_flow_ops._tensor_array_read(h, 0, tf.float32) r1 = gen_data_flow_ops._tensor_array_read(h, 1, tf.float32) r2 = gen_data_flow_ops._tensor_array_read(h, 2, tf.float32) with tf.control_dependencies(grad_writes): g_r0 = gen_data_flow_ops._tensor_array_read(g_h, 0, tf.float32) g_r1 = gen_data_flow_ops._tensor_array_read(g_h, 1, tf.float32) g_r2 = gen_data_flow_ops._tensor_array_read(g_h, 2, tf.float32) d0, d1, d2, g_d0, g_d1, g_d2 = sess.run([r0, r1, r2, g_r0, g_r1, g_r2]) self.assertAllEqual([[4.0, 5.0]], d0) self.assertAllEqual([[1.0]], d1) self.assertAllEqual(-3.0, d2) self.assertAllEqual([[5.0, 6.0]], g_d0) self.assertAllEqual([[2.0]], g_d1) self.assertAllEqual(-2.0, g_d2)
def _testMultiTensorArray(self, use_gpu): with self.test_session(use_gpu=use_gpu): h1 = gen_data_flow_ops._tensor_array( size=1, dtype=tf.float32, tensor_array_name="foo") with tf.control_dependencies([ gen_data_flow_ops._tensor_array_write(h1, 0, 4.0)]): r1 = gen_data_flow_ops._tensor_array_read(h1, 0, tf.float32) h2 = gen_data_flow_ops._tensor_array( size=1, dtype=tf.float32, tensor_array_name="bar") with tf.control_dependencies([ gen_data_flow_ops._tensor_array_write(h2, 0, 5.0)]): r2 = gen_data_flow_ops._tensor_array_read(h2, 0, tf.float32) r = r1 + r2 self.assertAllClose(9.0, r.eval())
def __init__(self, dtype, size=None, dynamic_size=None, tensor_array_name=None, handle=None, flow=None, name=None): """Construct a new TensorArray or wrap an existing TensorArray handle. Args: dtype: (required) data type of the TensorArray. size: (optional) int32 scalar `Tensor`: the size of the TensorArray. Required if handle is not provided. dynamic_size: (optional) Python bool: If true, writes to the TensorArray can grow the TensorArray past its initial size. Default: False. tensor_array_name: (optional) Python string: the name of the TensorArray. This is used when creating the TensorArray handle. If this value is set, handle should be None. handle: (optional) A `Tensor` handle to an existing TensorArray. If this is set, tensor_array_name should be None. flow: (optional) A float `Tensor` scalar coming from an existing TensorArray.flow. name: A name for the operation (optional). Raises: ValueError: if both handle and tensor_array_name are provided. TypeError: if handle is provided but is not a Tensor. """ if handle is not None and tensor_array_name: raise ValueError( "Cannot construct with both handle and tensor_array_name") if handle is not None and not isinstance(handle, ops.Tensor): raise TypeError("Handle must be a Tensor") if handle is None and size is None: raise ValueError("Size must be provided if handle is not provided") if handle is not None and size is not None: raise ValueError("Cannot provide both a handle and size " "at the same time") if handle is not None and dynamic_size is not None: raise ValueError("Cannot provide both a handle and dynamic_size " "at the same time") dynamic_size = dynamic_size or False self._dtype = dtype with ops.op_scope([handle, size, flow], name, "TensorArray") as scope: if handle is not None: self._handle = handle else: self._handle = gen_data_flow_ops._tensor_array( dtype=dtype, size=size, dynamic_size=dynamic_size, tensor_array_name=tensor_array_name, name=scope) if flow is not None: self._flow = flow else: self._flow = constant_op.constant(0, dtype=_dtypes.float32)
def testTensorArrayUnpackWrongMajorSizeFails(self): with self.test_session(): h = gen_data_flow_ops._tensor_array( dtype=tf.float32, tensor_array_name="foo", size=3) with self.assertRaisesOpError( r"Input value must have first dimension " r"equal to the array size \(2 vs. 3\)"): gen_data_flow_ops._tensor_array_unpack(h, [1.0, 2.0]).run()
def _testTensorArrayWriteMultipleFails(self, use_gpu): with self.test_session(use_gpu=use_gpu): h = gen_data_flow_ops._tensor_array( dtype=tf.float32, tensor_array_name="foo", size=3) with self.assertRaisesOpError( "Could not write to TensorArray index 2 because " "it has already been written to."): with tf.control_dependencies([ gen_data_flow_ops._tensor_array_write(h, 2, 3.0)]): gen_data_flow_ops._tensor_array_write(h, 2, 3.0).run()
def testTensorArrayPackNotAllValuesAvailableFails(self): with self.test_session(): h = gen_data_flow_ops._tensor_array( dtype=tf.float32, tensor_array_name="foo", size=3) with self.assertRaisesOpError( "Could not read from TensorArray index 1 " "because it has not yet been written to."): with tf.control_dependencies([ gen_data_flow_ops._tensor_array_write(h, 0, [[4.0, 5.0]])]): gen_data_flow_ops._tensor_array_pack(h, tf.float32).eval()
def _testWriteCloseTensorArray(self, use_gpu): with self.test_session(use_gpu=use_gpu) as sess: h = gen_data_flow_ops._tensor_array( dtype=tf.float32, tensor_array_name="foo", size=3) writes = [ gen_data_flow_ops._tensor_array_write(h, 0, [[4.0, 5.0]]), gen_data_flow_ops._tensor_array_write(h, 1, [3.0]), gen_data_flow_ops._tensor_array_write(h, 2, -1.0)] with tf.control_dependencies(writes): close = gen_data_flow_ops._tensor_array_close(h) sess.run(close)
def __init__(self, dtype, size=None, dynamic_size=None, tensor_array_name=None, handle=None, flow=None, name=None): """Construct a new TensorArray or wrap an existing TensorArray handle. Args: dtype: (required) data type of the TensorArray. size: (optional) int32 scalar `Tensor`: the size of the TensorArray. Required if handle is not provided. dynamic_size: (optional) Python bool: If true, writes to the TensorArray can grow the TensorArray past its initial size. Default: False. tensor_array_name: (optional) Python string: the name of the TensorArray. This is used when creating the TensorArray handle. If this value is set, handle should be None. handle: (optional) A `Tensor` handle to an existing TensorArray. If this is set, tensor_array_name should be None. flow: (optional) A float `Tensor` scalar coming from an existing TensorArray.flow. name: A name for the operation (optional). Raises: ValueError: if both handle and tensor_array_name are provided. TypeError: if handle is provided but is not a Tensor. """ if handle is not None and tensor_array_name: raise ValueError( "Cannot construct with both handle and tensor_array_name") if handle is not None and not isinstance(handle, ops.Tensor): raise TypeError("Handle must be a Tensor") if handle is None and size is None: raise ValueError("Size must be provided if handle is not provided") if handle is not None and size is not None: raise ValueError("Cannot provide both a handle and size " "at the same time") if handle is not None and dynamic_size is not None: raise ValueError("Cannot provide both a handle and dynamic_size " "at the same time") dynamic_size = dynamic_size or False self._dtype = dtype with ops.op_scope([handle, size, flow], name, "TensorArray") as scope: if handle is not None: self._handle = handle else: self._handle = gen_data_flow_ops._tensor_array( dtype=dtype, size=size, dynamic_size=dynamic_size, tensor_array_name=tensor_array_name, name=scope) if flow is not None: self._flow = flow else: self._flow = constant_op.constant(0, dtype=_dtypes.float32)
def _testTensorGradAccessTwiceReceiveSameObject(self, use_gpu): with self.test_session(use_gpu=use_gpu) as sess: h = gen_data_flow_ops._tensor_array( dtype=tf.float32, tensor_array_name="foo", size=3) g_h_0 = gen_data_flow_ops._tensor_array_grad(h) g_h_1 = gen_data_flow_ops._tensor_array_grad(h) with tf.control_dependencies([ gen_data_flow_ops._tensor_array_write(g_h_0, 0, [[4.0, 5.0]])]): # Write with one gradient handle, read with another copy of it r1_0 = gen_data_flow_ops._tensor_array_read(g_h_1, 0, tf.float32) t_g_h_0, t_g_h_1, d_r1_0 = sess.run([g_h_0, g_h_1, r1_0]) self.assertAllEqual(t_g_h_0, t_g_h_1) self.assertAllEqual([[4.0, 5.0]], d_r1_0)
def _testTensorArrayWriteGradientAddMultipleAddsType(self, use_gpu, dtype): with self.test_session(use_gpu=use_gpu): h = gen_data_flow_ops._tensor_array( dtype=dtype, tensor_array_name="foo", size=3) c = lambda x: np.asarray(x, dtype=dtype.as_numpy_dtype) writes = [ gen_data_flow_ops._tensor_array_write( h, 2, c(3.0), gradient_add=True), gen_data_flow_ops._tensor_array_write( h, 2, c(4.0), gradient_add=True)] with tf.control_dependencies(writes): self.assertAllEqual( c(7.00), gen_data_flow_ops._tensor_array_read(h, 2, dtype).eval())
def _testTensorArrayWriteWrongIndexOrDataTypeFails(self, use_gpu): with self.test_session(use_gpu=use_gpu): h = gen_data_flow_ops._tensor_array( dtype=tf.float32, tensor_array_name="foo", size=3) # Test writing the wrong datatype with self.assertRaisesOpError( "TensorArray dtype is float but Op is trying to write dtype string"): gen_data_flow_ops._tensor_array_write(h, -1, "wrong_type_scalar").run() # Test writing to a negative index with self.assertRaisesOpError( "Tried to write to index -1 but array size is: 3"): gen_data_flow_ops._tensor_array_write(h, -1, 3.0).run() # Test reading from too large an index with self.assertRaisesOpError( "Tried to write to index 3 but array size is: 3"): gen_data_flow_ops._tensor_array_write(h, 3, 3.0).run()
def _testTensorArrayWritePack(self, tf_dtype, use_gpu): dtype = tf_dtype.as_numpy_dtype() with self.test_session(use_gpu=use_gpu): h = gen_data_flow_ops._tensor_array( dtype=tf_dtype, tensor_array_name="foo", size=3) if tf_dtype == tf.string: convert = lambda x: np.asarray(x).astype(np.str) else: convert = lambda x: np.asarray(x).astype(dtype) writes = [ gen_data_flow_ops._tensor_array_write(h, 0, convert([[4.0, 5.0]])), gen_data_flow_ops._tensor_array_write(h, 1, convert([[6.0, 7.0]])), gen_data_flow_ops._tensor_array_write(h, 2, convert([[8.0, 9.0]]))] with tf.control_dependencies(writes): c0 = gen_data_flow_ops._tensor_array_pack(h, tf_dtype) self.assertAllEqual( convert([[[4.0, 5.0]], [[6.0, 7.0]], [[8.0, 9.0]]]), c0.eval())
def __init__(self, dtype, size, tensor_array_name=None, handle=None, name=None): """Construct a new TensorArray or wrap an existing TensorArray handle. Args: dtype: (required) data type of the TensorArray. size: (required) int32 scalar `Tensor`: the size of the TensorArray. tensor_array_name: (optional) Python string: the name of the TensorArray. This is used when creating the TensorArray handle. If this value is set, handle should be None. handle: (optional) A `Tensor` handle to an existing TensorArray. If this is set, tensor_array_name should be None. name: A name for the operation (optional). Raises: ValueError: if both handle and tensor_array_name are provided. """ if handle and tensor_array_name: raise ValueError( "Cannot construct with both handle and tensor_array_name") with ops.op_scope([handle, size], name, "TensorArray") as scope: if handle: self._handle = handle else: self._handle = gen_data_flow_ops._tensor_array( dtype=dtype, size=size, tensor_array_name=tensor_array_name, name=scope) self._flow = constant_op.constant(0, dtype=_dtypes.float32) self._dtype = dtype self._gradient_add = False
def _testTensorArrayUnpackRead(self, tf_dtype, use_gpu): dtype = tf_dtype.as_numpy_dtype() with self.test_session(use_gpu=use_gpu) as sess: h = gen_data_flow_ops._tensor_array( dtype=tf_dtype, tensor_array_name="foo", size=3) if tf_dtype == tf.string: convert = lambda x: np.asarray(x).astype(np.str) else: convert = lambda x: np.asarray(x).astype(dtype) # Unpack a vector into scalars with tf.control_dependencies([ gen_data_flow_ops._tensor_array_unpack( h, convert([1.0, 2.0, 3.0]))]): r0 = gen_data_flow_ops._tensor_array_read(h, 0, tf_dtype) r1 = gen_data_flow_ops._tensor_array_read(h, 1, tf_dtype) r2 = gen_data_flow_ops._tensor_array_read(h, 2, tf_dtype) d0, d1, d2 = sess.run([r0, r1, r2]) self.assertAllEqual(convert(1.0), d0) self.assertAllEqual(convert(2.0), d1) self.assertAllEqual(convert(3.0), d2) # Unpack a matrix into vectors with tf.control_dependencies([ gen_data_flow_ops._tensor_array_unpack( h, convert([[1.0, 1.1], [2.0, 2.1], [3.0, 3.1]]))]): r0 = gen_data_flow_ops._tensor_array_read(h, 0, tf_dtype) r1 = gen_data_flow_ops._tensor_array_read(h, 1, tf_dtype) r2 = gen_data_flow_ops._tensor_array_read(h, 2, tf_dtype) d0, d1, d2 = sess.run([r0, r1, r2]) self.assertAllEqual(convert([1.0, 1.1]), d0) self.assertAllEqual(convert([2.0, 2.1]), d1) self.assertAllEqual(convert([3.0, 3.1]), d2)
def _testCloseTensorArray(self, use_gpu): with self.test_session(use_gpu=use_gpu) as sess: h = gen_data_flow_ops._tensor_array( dtype=tf.float32, tensor_array_name="foo", size=3) c1 = gen_data_flow_ops._tensor_array_close(h) sess.run(c1)
def __init__(self, dtype, size=None, dynamic_size=None, clear_after_read=None, tensor_array_name=None, handle=None, flow=None, infer_shape=True, name=None): """Construct a new TensorArray or wrap an existing TensorArray handle. Args: dtype: (required) data type of the TensorArray. size: (optional) int32 scalar `Tensor`: the size of the TensorArray. Required if handle is not provided. dynamic_size: (optional) Python bool: If true, writes to the TensorArray can grow the TensorArray past its initial size. Default: False. clear_after_read: Boolean (optional, default: True). If True, clear TensorArray values after reading them. This disables read-many semantics, but allows early release of memory. tensor_array_name: (optional) Python string: the name of the TensorArray. This is used when creating the TensorArray handle. If this value is set, handle should be None. handle: (optional) A `Tensor` handle to an existing TensorArray. If this is set, tensor_array_name should be None. flow: (optional) A float `Tensor` scalar coming from an existing `TensorArray.flow`. infer_shape: (optional, default: True) If True, shape inference is enabled. In this case, all elements must have the same shape. name: A name for the operation (optional). Raises: ValueError: if both handle and tensor_array_name are provided. TypeError: if handle is provided but is not a Tensor. """ if handle is not None and tensor_array_name: raise ValueError( "Cannot construct with both handle and tensor_array_name") if handle is not None and not isinstance(handle, ops.Tensor): raise TypeError("Handle must be a Tensor") if handle is None and size is None: raise ValueError("Size must be provided if handle is not provided") if handle is not None and size is not None: raise ValueError("Cannot provide both a handle and size " "at the same time") if handle is not None and dynamic_size is not None: raise ValueError("Cannot provide both a handle and dynamic_size " "at the same time") if handle is not None and clear_after_read is not None: raise ValueError( "Cannot provide both a handle and clear_after_read " "at the same time") if clear_after_read is None: clear_after_read = True dynamic_size = dynamic_size or False self._dtype = dtype self._infer_shape = infer_shape # Record the current static shape for the array elements. The first # write adds the shape of the tensor it writes, and all subsequent # writes checks for shape equality. self._elem_shape = [] with ops.op_scope([handle, size, flow], name, "TensorArray") as scope: if handle is not None: self._handle = handle else: if flow is not None: with ops.colocate_with(flow): self._handle = gen_data_flow_ops._tensor_array( dtype=dtype, size=size, dynamic_size=dynamic_size, clear_after_read=clear_after_read, tensor_array_name=tensor_array_name, name=scope) else: self._handle = gen_data_flow_ops._tensor_array( dtype=dtype, size=size, dynamic_size=dynamic_size, clear_after_read=clear_after_read, tensor_array_name=tensor_array_name, name=scope) if flow is not None: self._flow = flow else: with ops.colocate_with(self._handle): self._flow = constant_op.constant(0, dtype=_dtypes.float32)
def __init__( self, dtype, size=None, dynamic_size=None, clear_after_read=None, tensor_array_name=None, handle=None, flow=None, infer_shape=True, name=None, ): """Construct a new TensorArray or wrap an existing TensorArray handle. A note about the parameter `name`: The name of the `TensorArray` (even if passed in) is uniquified: each time a new `TensorArray` is created at runtime it is assigned its own name for the duration of the run. This avoids name collissions if a `TensorArray` is created within a `while_loop`. Args: dtype: (required) data type of the TensorArray. size: (optional) int32 scalar `Tensor`: the size of the TensorArray. Required if handle is not provided. dynamic_size: (optional) Python bool: If true, writes to the TensorArray can grow the TensorArray past its initial size. Default: False. clear_after_read: Boolean (optional, default: True). If True, clear TensorArray values after reading them. This disables read-many semantics, but allows early release of memory. tensor_array_name: (optional) Python string: the name of the TensorArray. This is used when creating the TensorArray handle. If this value is set, handle should be None. handle: (optional) A `Tensor` handle to an existing TensorArray. If this is set, tensor_array_name should be None. flow: (optional) A float `Tensor` scalar coming from an existing `TensorArray.flow`. infer_shape: (optional, default: True) If True, shape inference is enabled. In this case, all elements must have the same shape. name: A name for the operation (optional). Raises: ValueError: if both handle and tensor_array_name are provided. TypeError: if handle is provided but is not a Tensor. """ if handle is not None and tensor_array_name: raise ValueError("Cannot construct with both handle and tensor_array_name") if handle is not None and not isinstance(handle, ops.Tensor): raise TypeError("Handle must be a Tensor") if handle is None and size is None: raise ValueError("Size must be provided if handle is not provided") if handle is not None and size is not None: raise ValueError("Cannot provide both a handle and size " "at the same time") if handle is not None and dynamic_size is not None: raise ValueError("Cannot provide both a handle and dynamic_size " "at the same time") if handle is not None and clear_after_read is not None: raise ValueError("Cannot provide both a handle and clear_after_read " "at the same time") if clear_after_read is None: clear_after_read = True dynamic_size = dynamic_size or False self._dtype = dtype self._infer_shape = infer_shape # Record the current static shape for the array elements. The first # write adds the shape of the tensor it writes, and all subsequent # writes checks for shape equality. self._elem_shape = [] with ops.op_scope([handle, size, flow], name, "TensorArray") as scope: if handle is not None: self._handle = handle else: if flow is not None: with ops.colocate_with(flow): self._handle = gen_data_flow_ops._tensor_array( dtype=dtype, size=size, dynamic_size=dynamic_size, clear_after_read=clear_after_read, tensor_array_name=tensor_array_name, name=scope, ) else: self._handle = gen_data_flow_ops._tensor_array( dtype=dtype, size=size, dynamic_size=dynamic_size, clear_after_read=clear_after_read, tensor_array_name=tensor_array_name, name=scope, ) if flow is not None: self._flow = flow else: with ops.colocate_with(self._handle): self._flow = constant_op.constant(0, dtype=_dtypes.float32)