def test_works_with_registered(self): class CustomClass(object): def value(self): return tf.convert_to_tensor(42.) tf.register_tensor_conversion_function( CustomClass, lambda value, **_: value.value()) tf_utils.register_symbolic_tensor_type(CustomClass) if tf.executing_eagerly(): self.assertFalse( tf_utils.is_symbolic_tensor( tf.Variable(name='blah', initial_value=0.))) self.assertFalse( tf_utils.is_symbolic_tensor(tf.convert_to_tensor(0.))) self.assertFalse( tf_utils.is_symbolic_tensor( tf.SparseTensor(indices=[[0, 0], [1, 2]], values=[1, 2], dense_shape=[3, 4]))) self.assertFalse(tf_utils.is_symbolic_tensor(CustomClass())) else: self.assertTrue( tf_utils.is_symbolic_tensor( tf.Variable(name='blah', initial_value=0.))) self.assertTrue( tf_utils.is_symbolic_tensor(tf.convert_to_tensor(0.))) self.assertTrue( tf_utils.is_symbolic_tensor( tf.SparseTensor(indices=[[0, 0], [1, 2]], values=[1, 2], dense_shape=[3, 4]))) self.assertTrue(tf_utils.is_symbolic_tensor(CustomClass()))
def apply_gradients(self, grads_and_vars, **kwargs): """Wrapped apply_gradient method. Returns an operation to be executed. """ for spec in self.optimizer_specs: spec["gv"] = [] for grad, var in tuple(grads_and_vars): for spec in self.optimizer_specs: for name in spec["weights"]: if var.name == name: spec["gv"].append((grad, var)) update_ops = [ spec["optimizer"].apply_gradients(spec["gv"], **kwargs) for spec in self.optimizer_specs ] update_group = tf.group(update_ops) any_symbolic = any( isinstance(i, tf.Operation) or tf_utils.is_symbolic_tensor(i) for i in update_ops) if not tf.executing_eagerly() or any_symbolic: # If the current context is graph mode or any of the update ops are # symbolic then the step update should be carried out under a graph # context. (eager updates execute immediately) with backend._current_graph( # pylint: disable=protected-access update_ops).as_default(): with tf.control_dependencies([update_group]): return self.iterations.assign_add(1, read_value=False) return self.iterations.assign_add(1)
def test_dict_eager(self): if not tf.executing_eagerly(): self.skipTest('Run in eager mode only.') with testing_utils.use_keras_tensors_scope(False): a = {'b': np.ones(10), 'a': np.ones(20)} model_inputs = training_utils_v1.ModelInputs(a) self.assertEqual(['a', 'b'], model_inputs.get_input_names()) vals = model_inputs.get_symbolic_inputs() self.assertTrue(tf_utils.is_symbolic_tensor(vals['a'])) self.assertTrue(tf_utils.is_symbolic_tensor(vals['b'])) with testing_utils.use_keras_tensors_scope(True): a = {'b': np.ones(10), 'a': np.ones(20)} model_inputs = training_utils_v1.ModelInputs(a) self.assertEqual(['a', 'b'], model_inputs.get_input_names()) vals = model_inputs.get_symbolic_inputs() self.assertIsInstance(vals['a'], keras_tensor.KerasTensor) self.assertIsInstance(vals['b'], keras_tensor.KerasTensor)
def test_simple_build_with_constant(self): class BuildConstantLayer(keras.layers.Layer): def build(self, input_shape): self.b = tf.convert_to_tensor(2.0) def call(self, inputs): return self.b * inputs layer = BuildConstantLayer() model = testing_utils.get_model_from_layers( [layer, keras.layers.Dense(1)], input_shape=(1, )) x = tf.convert_to_tensor([[3.0]]) self.assertEqual(tf_utils.is_symbolic_tensor(model(x)), not tf.executing_eagerly()) self.assertEqual(tf_utils.is_symbolic_tensor(layer(x)), not tf.executing_eagerly()) self.assertAllClose(keras.backend.get_value(layer(x)), [[6.0]])
def test_build_with_derived_constant(self): class BuildDerivedConstantLayer(keras.layers.Layer): def build(self, input_shape): a = tf.convert_to_tensor(1.0) b = 2.0 * a self.variable = tf.Variable(b) self.constant = tf.convert_to_tensor(self.variable) def call(self, inputs): return self.variable * self.constant * inputs layer = BuildDerivedConstantLayer() model = testing_utils.get_model_from_layers( [layer, keras.layers.Dense(1)], input_shape=(1, )) x = tf.convert_to_tensor([[3.0]]) self.assertEqual(tf_utils.is_symbolic_tensor(model(x)), not tf.executing_eagerly()) self.assertEqual(tf_utils.is_symbolic_tensor(layer(x)), not tf.executing_eagerly()) self.assertAllClose(keras.backend.get_value(layer(x)), [[12.0]])
def test_default_behavior(self): if tf.executing_eagerly(): self.assertFalse( tf_utils.is_symbolic_tensor( tf.Variable(name="blah", initial_value=0.0))) self.assertFalse( tf_utils.is_symbolic_tensor(tf.convert_to_tensor(0.0))) self.assertFalse( tf_utils.is_symbolic_tensor( tf.SparseTensor( indices=[[0, 0], [1, 2]], values=[1, 2], dense_shape=[3, 4], ))) else: self.assertTrue( tf_utils.is_symbolic_tensor( tf.Variable(name="blah", initial_value=0.0))) self.assertTrue( tf_utils.is_symbolic_tensor(tf.convert_to_tensor(0.0))) self.assertTrue( tf_utils.is_symbolic_tensor( tf.SparseTensor( indices=[[0, 0], [1, 2]], values=[1, 2], dense_shape=[3, 4], )))
def test_single_thing_eager(self): if not tf.executing_eagerly(): self.skipTest('Run in eager mode only.') with testing_utils.use_keras_tensors_scope(False): a = np.ones(10, dtype=np.int32) model_inputs = training_utils_v1.ModelInputs(a) self.assertEqual(['input_1'], model_inputs.get_input_names()) val = model_inputs.get_symbolic_inputs() self.assertTrue(tf_utils.is_symbolic_tensor(val)) vals = model_inputs.get_symbolic_inputs(return_single_as_list=True) self.assertEqual(1, len(vals)) self.assertTrue(tf_utils.is_symbolic_tensor(vals[0])) self.assertEqual(tf.int32, vals[0].dtype) with testing_utils.use_keras_tensors_scope(True): a = np.ones(10, dtype=np.int32) model_inputs = training_utils_v1.ModelInputs(a) self.assertEqual(['input_1'], model_inputs.get_input_names()) val = model_inputs.get_symbolic_inputs() self.assertIsInstance(val, keras_tensor.KerasTensor) vals = model_inputs.get_symbolic_inputs(return_single_as_list=True) self.assertEqual(1, len(vals)) self.assertIsInstance(vals[0], keras_tensor.KerasTensor) self.assertEqual(tf.int32, vals[0].dtype)
def __init__( self, input_shape=None, batch_size=None, dtype=None, input_tensor=None, sparse=None, name=None, ragged=None, type_spec=None, **kwargs, ): self._init_input_shape = input_shape self._init_batch_size = batch_size self._init_dtype = dtype self._init_sparse = sparse self._init_ragged = ragged self._init_type_spec = type_spec strategy = tf.distribute.get_strategy() if (strategy and batch_size is not None and distributed_training_utils.global_batch_size_supported( strategy)): if batch_size % strategy.num_replicas_in_sync != 0: raise ValueError( "The `batch_size` argument ({}) must be divisible by " "the number of replicas ({})".format( batch_size, strategy.num_replicas_in_sync)) batch_size = batch_size // strategy.num_replicas_in_sync if "batch_input_shape" in kwargs: batch_input_shape = kwargs.pop("batch_input_shape") if input_shape and batch_input_shape: raise ValueError("Only provide the input_shape OR " "batch_input_shape argument to " "InputLayer, not both at the same time.") # Set the input shape and batch size from the batch_input_shape. # Note that batch_input_shape can be None (unknown rank) or [] (scalar), # in which case the batch size must be None. if batch_input_shape: batch_size = batch_input_shape[0] input_shape = batch_input_shape[1:] if kwargs: raise ValueError( f"Unrecognized keyword arguments: {list(kwargs.keys())}") if sparse and ragged: raise ValueError( "Cannot set both sparse and ragged to True in a Keras input.") if not name: prefix = "input" name = prefix + "_" + str(backend.get_uid(prefix)) if not dtype: if input_tensor is None: dtype = backend.floatx() else: dtype = backend.dtype(input_tensor) elif input_tensor is not None and input_tensor.dtype != dtype: raise ValueError( "`input_tensor.dtype` differs from `dtype`. Received: " f"input_tensor.dtype={input_tensor.dtype} " f"but expected dtype={dtype}") super().__init__(dtype=dtype, name=name) self.built = True self.sparse = True if sparse else False self.ragged = True if ragged else False self.batch_size = batch_size self.supports_masking = True if isinstance(input_shape, tf.TensorShape): input_shape = tuple(input_shape.as_list()) elif isinstance(input_shape, int): input_shape = (input_shape, ) if type_spec is not None: args_that_must_be_none = [ ("(input_)shape", self._init_input_shape), ("batch_size", self._init_batch_size), ("dtype", self._init_dtype), ("input_tensor", input_tensor), ("sparse", self._init_sparse), ("ragged", self._init_ragged), ] for arg_name, arg in args_that_must_be_none: _assert_other_arg_none(arg_name, arg) if not tf.compat.v1.executing_eagerly_outside_functions(): raise ValueError( "Creating Keras inputs from a type_spec is only " "supported when eager execution is enabled.") input_tensor = keras_tensor.keras_tensor_from_type_spec(type_spec) if isinstance(input_tensor, keras_tensor.SparseKerasTensor): self.sparse = True if isinstance(input_tensor, keras_tensor.RaggedKerasTensor): self.ragged = True self.is_placeholder = True try: self._batch_input_shape = tuple(input_tensor.shape.as_list()) except ValueError: # If the shape cannot be represented as a tuple (e.g. unknown rank) self._batch_input_shape = None elif input_tensor is None: if input_shape is not None: batch_input_shape = (batch_size, ) + tuple(input_shape) else: batch_input_shape = None graph = backend.get_graph() with graph.as_default(): input_tensor = backend.placeholder( shape=batch_input_shape, dtype=dtype, name=self.name, sparse=sparse, ragged=ragged, ) self.is_placeholder = True self._batch_input_shape = batch_input_shape else: if tf.compat.v1.executing_eagerly_outside_functions(): if not isinstance(input_tensor, keras_tensor.KerasTensor): input_tensor = keras_tensor.keras_tensor_from_tensor( input_tensor) else: if not tf_utils.is_symbolic_tensor(input_tensor): raise ValueError( "You should not pass an EagerTensor to `Input`. " "For example, instead of creating an " "`InputLayer`, you should instantiate your model " "and directly call it on your input.") self.is_placeholder = False try: self._batch_input_shape = tuple(input_tensor.shape.as_list()) except ValueError: # If the shape cannot be represented as a tuple (e.g. unknown rank) self._batch_input_shape = None # Create an input node. input_tensor._keras_mask = None node_module.Node(layer=self, outputs=input_tensor) # Store type spec if isinstance(input_tensor, keras_tensor.KerasTensor) or ( tf_utils.is_extension_type(input_tensor)): self._type_spec = (input_tensor._type_spec) # pylint: disable=protected-access else: self._type_spec = tf.TensorSpec( shape=input_tensor.shape, dtype=input_tensor.dtype, name=self.name, )
def __init__(self, input_shape=None, batch_size=None, dtype=None, input_tensor=None, sparse=None, name=None, ragged=None, type_spec=None, **kwargs): self._init_input_shape = input_shape self._init_batch_size = batch_size self._init_dtype = dtype self._init_sparse = sparse self._init_ragged = ragged self._init_type_spec = type_spec strategy = tf.distribute.get_strategy() if strategy and batch_size is not None and \ distributed_training_utils.global_batch_size_supported(strategy): if batch_size % strategy.num_replicas_in_sync != 0: raise ValueError( 'The `batch_size` argument ({}) must be divisible by ' 'the number of replicas ({})'.format( batch_size, strategy.num_replicas_in_sync)) batch_size = batch_size // strategy.num_replicas_in_sync if 'batch_input_shape' in kwargs: batch_input_shape = kwargs.pop('batch_input_shape') if input_shape and batch_input_shape: raise ValueError('Only provide the input_shape OR ' 'batch_input_shape argument to ' 'InputLayer, not both at the same time.') batch_size = batch_input_shape[0] input_shape = batch_input_shape[1:] if kwargs: raise ValueError('Unrecognized keyword arguments:', kwargs.keys()) if sparse and ragged: raise ValueError( 'Cannot set both sparse and ragged to True in a Keras input.') if not name: prefix = 'input' name = prefix + '_' + str(backend.get_uid(prefix)) if not dtype: if input_tensor is None: dtype = backend.floatx() else: dtype = backend.dtype(input_tensor) elif input_tensor is not None and input_tensor.dtype != dtype: raise ValueError( '`input_tensor.dtype` differs from `dtype`: %s vs. %s' % (input_tensor.dtype, dtype)) super(InputLayer, self).__init__(dtype=dtype, name=name) self.built = True self.sparse = True if sparse else False self.ragged = True if ragged else False self.batch_size = batch_size self.supports_masking = True if isinstance(input_shape, tf.TensorShape): input_shape = tuple(input_shape.as_list()) elif isinstance(input_shape, int): input_shape = (input_shape, ) if type_spec is not None: args_that_must_be_none = [ ('(input_)shape', self._init_input_shape), ('batch_size', self._init_batch_size), ('dtype', self._init_dtype), ('input_tensor', input_tensor), ('sparse', self._init_sparse), ('ragged', self._init_ragged), ] for arg_name, arg in args_that_must_be_none: _assert_other_arg_none(arg_name, arg) if not keras_tensor.keras_tensors_enabled(): raise ValueError( 'Creating Keras inputs from a type_spec is only ' 'supported when eager execution is enabled.') input_tensor = keras_tensor.keras_tensor_from_type_spec(type_spec) if isinstance(input_tensor, keras_tensor.SparseKerasTensor): self.sparse = True if isinstance(input_tensor, keras_tensor.RaggedKerasTensor): self.ragged = True self.is_placeholder = True try: self._batch_input_shape = tuple(input_tensor.shape.as_list()) except ValueError: # If the shape cannot be represented as a tuple (e.g. unknown rank) self._batch_input_shape = None elif input_tensor is None: if input_shape is not None: batch_input_shape = (batch_size, ) + tuple(input_shape) else: batch_input_shape = None graph = backend.get_graph() with graph.as_default(): input_tensor = backend.placeholder(shape=batch_input_shape, dtype=dtype, name=self.name, sparse=sparse, ragged=ragged) self.is_placeholder = True self._batch_input_shape = batch_input_shape else: if keras_tensor.keras_tensors_enabled(): if not isinstance(input_tensor, keras_tensor.KerasTensor): input_tensor = keras_tensor.keras_tensor_from_tensor( input_tensor) else: if not tf_utils.is_symbolic_tensor(input_tensor): raise ValueError( 'You should not pass an EagerTensor to `Input`. ' 'For example, instead of creating an ' 'InputLayer, you should instantiate your model and ' 'directly call it on your input.') self.is_placeholder = False try: self._batch_input_shape = tuple(input_tensor.shape.as_list()) except ValueError: # If the shape cannot be represented as a tuple (e.g. unknown rank) self._batch_input_shape = None # Create an input node. input_tensor._keras_mask = None node_module.Node(layer=self, outputs=input_tensor) # Store type spec if isinstance(input_tensor, keras_tensor.KerasTensor) or ( tf_utils.is_extension_type(input_tensor)): self._type_spec = input_tensor._type_spec # pylint: disable=protected-access else: self._type_spec = tf.TensorSpec(shape=input_tensor.shape, dtype=input_tensor.dtype, name=self.name)