def test_recursive_model(self): Input = keras.layers.Input Dense = keras.layers.Dense Add = keras.layers.Add N, C, D = 2, 3, 3 x = np.random.rand(N, C).astype(np.float32, copy=False) sub_input1 = Input(shape=(C,)) sub_mapped1 = Dense(D)(sub_input1) sub_model1 = keras.Model(inputs=sub_input1, outputs=sub_mapped1) sub_input2 = Input(shape=(C,)) sub_mapped2 = Dense(D)(sub_input2) sub_model2 = keras.Model(inputs=sub_input2, outputs=sub_mapped2) input1 = Input(shape=(D,)) input2 = Input(shape=(D,)) mapped1_2 = sub_model1(input1) mapped2_2 = sub_model2(input2) sub_sum = Add()([mapped1_2, mapped2_2]) keras_model = keras.Model(inputs=[input1, input2], outputs=sub_sum) onnx_model = keras2onnx.convert_keras(keras_model, keras_model.name) x = [x, 2 * x] expected = keras_model.predict(x) self.assertTrue(self.run_onnx_runtime('recursive', onnx_model, x, expected))
def test_recursive_and_shared_model(self): Input = keras.layers.Input Dense = keras.layers.Dense Add = keras.layers.Add Activation = keras.layers.Activation N, C, D = 2, 3, 3 x = np.random.rand(N, C).astype(np.float32, copy=False) sub_input1 = Input(shape=(C,)) sub_mapped1 = Dense(D)(sub_input1) sub_output1 = Activation('sigmoid')(sub_mapped1) sub_model1 = keras.Model(inputs=sub_input1, outputs=sub_output1) sub_input2 = Input(shape=(C,)) sub_mapped2 = sub_model1(sub_input2) sub_output2 = Activation('tanh')(sub_mapped2) sub_model2 = keras.Model(inputs=sub_input2, outputs=sub_output2) input1 = Input(shape=(D,)) input2 = Input(shape=(D,)) mapped1_1 = Activation('tanh')(input1) mapped2_1 = Activation('sigmoid')(input2) mapped1_2 = sub_model1(mapped1_1) mapped1_3 = sub_model1(mapped1_2) mapped2_2 = sub_model2(mapped2_1) sub_sum = Add()([mapped1_3, mapped2_2]) keras_model = keras.Model(inputs=[input1, input2], outputs=sub_sum) keras_model.compile('sgd', loss='mse') onnx_model = keras2onnx.convert_keras(keras_model, keras_model.name, debug_mode=True) x = [x, 2 * x] expected = keras_model.predict(x) self.assertTrue(self.run_onnx_runtime('recursive_and_shared', onnx_model, x, expected))
def test_GRU(self): GRU = keras.layers.GRU inputs1 = keras.Input(shape=(3, 1)) cls = GRU(2, return_state=False, return_sequences=False) oname = cls(inputs1) model = keras.Model(inputs=inputs1, outputs=[oname]) onnx_model = keras2onnx.convert_keras(model, model.name) data = np.array([0.1, 0.2, 0.3]).astype(np.float32).reshape((1, 3, 1)) expected = model.predict(data) self.assertTrue(self.run_onnx_runtime(onnx_model.graph.name, onnx_model, data, expected)) # GRU with initial state for return_sequences in [True, False]: cls = GRU(2, return_state=False, return_sequences=return_sequences) initial_state_input = keras.Input(shape=(2, )) oname = cls(inputs1, initial_state=initial_state_input) model = keras.Model(inputs=[inputs1, initial_state_input], outputs=[oname]) onnx_model = keras2onnx.convert_keras(model, model.name) data = np.array([0.1, 0.2, 0.3]).astype(np.float32).reshape((1, 3, 1)) init_state = np.array([0.4, 0.5]).astype(np.float32).reshape((1, 2)) init_state_onnx = np.array([0.4, 0.5]).astype(np.float32).reshape((1, 1, 2)) expected = model.predict([data, init_state]) self.assertTrue(self.run_onnx_runtime(onnx_model.graph.name, onnx_model, [data, init_state_onnx], expected))
def test_Bidirectional(self): for return_sequences in [True, False]: input_dim = 10 sequence_len = 5 model = keras.Sequential() model.add(keras.layers.Bidirectional(keras.layers.LSTM(10, return_sequences=return_sequences), input_shape=(5, 10))) model.add(keras.layers.Dense(5)) model.add(keras.layers.Activation('softmax')) model.compile(loss='categorical_crossentropy', optimizer='rmsprop') onnx_model = keras2onnx.convert_keras(model, 'test') data = np.random.rand(input_dim, sequence_len).astype(np.float32).reshape((1, sequence_len, input_dim)) expected = model.predict(data) self.assertTrue(self.run_onnx_runtime('bidirectional', onnx_model, data, expected)) for merge_mode in ['concat', None]: # TODO: case return_sequences=False for return_sequences in [True]: input_dim = 10 sequence_len = 5 sub_input1 = keras.layers.Input(shape=(sequence_len, input_dim)) sub_mapped1 = keras.layers.Bidirectional(keras.layers.LSTM(10, return_sequences=return_sequences), input_shape=(5, 10), merge_mode=merge_mode)(sub_input1) keras_model = keras.Model(inputs=sub_input1, outputs=sub_mapped1) onnx_model = keras2onnx.convert_keras(keras_model, 'test_2') data = np.random.rand(input_dim, sequence_len).astype(np.float32).reshape((1, sequence_len, input_dim)) expected = keras_model.predict(data) self.assertTrue(self.run_onnx_runtime('bidirectional', onnx_model, data, expected))
def test_deep_speech_2(self): K.clear_session() input_dim = 20 output_dim = 10 rnn_units = 800 # Define input tensor [batch, time, features] input_tensor = layers.Input([None, input_dim], name='X') # Add 4th dimension [batch, time, frequency, channel] x = layers.Lambda(keras.backend.expand_dims, arguments=dict(axis=-1))(input_tensor) x = layers.Conv2D(filters=32, kernel_size=[11, 41], strides=[2, 2], padding='same', use_bias=False, name='conv_1')(x) x = layers.BatchNormalization(name='conv_1_bn')(x) x = layers.ReLU(name='conv_1_relu')(x) x = layers.Conv2D(filters=32, kernel_size=[11, 21], strides=[1, 2], padding='same', use_bias=False, name='conv_2')(x) x = layers.BatchNormalization(name='conv_2_bn')(x) x = layers.ReLU(name='conv_2_relu')(x) # We need to squeeze to 3D tensor. Thanks to the stride in frequency # domain, we reduce the number of features four times for each channel. x = layers.Reshape([-1, input_dim//4*32])(x) for i in [1, 2, 3, 4, 5]: recurrent = layers.GRU(units=rnn_units, activation='tanh', recurrent_activation='sigmoid', use_bias=True, return_sequences=True, reset_after=True, name='gru_'+str(i)) x = layers.Bidirectional(recurrent, name='bidirectional'+str(i), merge_mode='concat')(x) x = layers.Dropout(rate=0.5)(x) if i < 5 else x # Only between # Return at each time step logits along characters. Then CTC # computation is more stable, in contrast to the softmax. x = layers.TimeDistributed(layers.Dense(units=rnn_units*2), name='dense_1')(x) x = layers.ReLU(name='dense_1_relu')(x) x = layers.Dropout(rate=0.5)(x) output_tensor = layers.TimeDistributed(layers.Dense(units=output_dim), name='dense_2')(x) model = keras.Model(input_tensor, output_tensor, name='DeepSpeech2') data = np.random.rand(2, 3, input_dim).astype(np.float32) expected = model.predict(data) onnx_model = keras2onnx.convert_keras(model, model.name) self.assertTrue( run_keras_and_ort(onnx_model.graph.name, onnx_model, model, data, expected, self.model_files))
def test_custom(self): from efficientnet import tfkeras as efn keras.backend.set_learning_phase(0) base_model = efn.EfficientNetB0(input_shape=(600, 600, 3), weights=None) backbone = keras.Model(base_model.input, base_model.get_layer("top_activation").output) res = run_image(backbone, self.model_files, img_path, target_size=(600, 600), rtol=1e-2, atol=1e-1, tf_v2=True) self.assertTrue(*res)
def test_LSTM(self): LSTM = keras.layers.LSTM inputs1 = keras.Input(shape=(3, 5)) for use_bias in [True, False]: cls = LSTM(units=2, return_state=True, return_sequences=True, use_bias=use_bias) lstm1, state_h, state_c = cls(inputs1) model = keras.Model(inputs=inputs1, outputs=[lstm1, state_h, state_c]) data = np.random.rand(3, 5).astype(np.float32).reshape((1, 3, 5)) onnx_model = keras2onnx.convert_keras(model, model.name) expected = model.predict(data) self.assertTrue(self.run_onnx_runtime(onnx_model.graph.name, onnx_model, data, expected))
def test_LSTM_with_bias(self): LSTM = keras.layers.LSTM inputs1 = keras.Input(shape=(1, 1)) cls = LSTM(units=1, return_state=True, return_sequences=True) lstm1, state_h, state_c = cls(inputs1) model = keras.Model(inputs=inputs1, outputs=[lstm1, state_h, state_c]) # Set weights: kernel, recurrent_kernel and bias model.set_weights([[[1, 2, 3, 4]], [[5, 6, 7, 8]], [1, 2, 3, 4]]) data = np.random.rand(1, 1).astype(np.float32).reshape((1, 1, 1)) onnx_model = keras2onnx.convert_keras(model, model.name) expected = model.predict(data) self.assertTrue(self.run_onnx_runtime(onnx_model.graph.name, onnx_model, data, expected))
def test_simpleRNN(self): inputs1 = keras.Input(shape=(3, 1)) cls = keras.layers.SimpleRNN(2, return_state=False, return_sequences=True) oname = cls(inputs1) # , initial_state=t0) model = keras.Model(inputs=inputs1, outputs=[oname]) onnx_model = keras2onnx.convert_keras(model, model.name) data = np.array([0.1, 0.2, 0.3]).astype(np.float32).reshape((1, 3, 1)) expected = model.predict(data) self.assertTrue(self.run_onnx_runtime(onnx_model.graph.name, onnx_model, data, expected)) # with initial state inputs2 = keras.Input(shape=(1, 2)) state = keras.Input(shape=(5,)) hidden_1 = keras.layers.SimpleRNN(5, activation='relu', return_sequences=True)(inputs2, initial_state=[state]) output = keras.layers.Dense(2, activation='sigmoid')(hidden_1) keras_model = keras.Model(inputs=[inputs2, state], outputs=output) onnx_model = keras2onnx.convert_keras(keras_model, keras_model.name, debug_mode=True) N, H, W, C = 3, 1, 2, 5 x = np.random.rand(N, H, W).astype(np.float32, copy=False) s = np.random.rand(N, C).astype(np.float32, copy=False) expected = keras_model.predict([x, s]) self.assertTrue(self.run_onnx_runtime(onnx_model.graph.name, onnx_model, [x, s], expected)) # with initial state and output state input = keras.Input(shape=(1, 2)) state_in = keras.Input(shape=(10,)) hidden_1, state_out = keras.layers.SimpleRNN(10, activation='relu', return_sequences=True, return_state=True)(input, initial_state=[state_in]) output = keras.layers.Dense(2, activation='linear')(hidden_1) keras_model = keras.Model(inputs=[input, state_in], outputs=[output, state_out]) onnx_model = keras2onnx.convert_keras(keras_model, keras_model.name) N, H, W, C = 3, 1, 2, 10 x = np.random.rand(N, H, W).astype(np.float32, copy=False) s = np.random.rand(N, C).astype(np.float32, copy=False) expected = keras_model.predict([x, s]) self.assertTrue(self.run_onnx_runtime(onnx_model.graph.name, onnx_model, [x, s], expected))
def test_LSTM_reshape(self): input_dim = 7 sequence_len = 3 inputs1 = keras.Input(shape=(sequence_len, input_dim)) cls = keras.layers.LSTM(units=5, return_state=False, return_sequences=True) lstm1 = cls(inputs1) output = keras.layers.Reshape((sequence_len, 5))(lstm1) model = keras.Model(inputs=inputs1, outputs=output) model.compile(optimizer='sgd', loss='mse') onnx_model = keras2onnx.convert_keras(model, 'test') data = np.random.rand(input_dim, sequence_len).astype(np.float32).reshape((1, sequence_len, input_dim)) expected = model.predict(data) self.assertTrue(self.run_onnx_runtime('tf_lstm', onnx_model, data, expected))
def test_deep_speech(self): K.clear_session() input_dim = 20 output_dim = 10 context = 7 units = 1024 dropouts = (0.1, 0.1, 0) # Define input tensor [batch, time, features] input_tensor = layers.Input([None, input_dim], name='X') # Add 4th dimension [batch, time, frequency, channel] x = layers.Lambda(keras.backend.expand_dims, arguments=dict(axis=-1))(input_tensor) # Fill zeros around time dimension x = layers.ZeroPadding2D(padding=(context, 0))(x) # Convolve signal in time dim receptive_field = (2 * context + 1, input_dim) x = layers.Conv2D(filters=units, kernel_size=receptive_field)(x) # Squeeze into 3rd dim array x = layers.Lambda(keras.backend.squeeze, arguments=dict(axis=2))(x) # Add non-linearity x = layers.ReLU(max_value=20)(x) # Use dropout as regularization x = layers.Dropout(rate=dropouts[0])(x) # 2nd and 3rd FC layers do a feature extraction base on a narrow # context of convolutional layer x = layers.TimeDistributed(layers.Dense(units))(x) x = layers.ReLU(max_value=20)(x) x = layers.Dropout(rate=dropouts[1])(x) x = layers.TimeDistributed(layers.Dense(units))(x) x = layers.ReLU(max_value=20)(x) x = layers.Dropout(rate=dropouts[2])(x) # Use recurrent layer to have a broader context x = layers.Bidirectional(layers.LSTM(units, return_sequences=True), merge_mode='sum')(x) # Return at each time step logits along characters. Then CTC # computation is more stable, in contrast to the softmax. output_tensor = layers.TimeDistributed(layers.Dense(output_dim))(x) model = keras.Model(input_tensor, output_tensor, name='DeepSpeech') data = np.random.rand(2, 3, input_dim).astype(np.float32) expected = model.predict(data) onnx_model = keras2onnx.convert_keras(model, model.name) self.assertTrue( run_keras_and_ort(onnx_model.graph.name, onnx_model, model, data, expected, self.model_files))