Я вырываю себе волосы этим.
Я задал вопрос здесь Если потом внутри нестандартного не обучаемого слоя керас , но у меня все еще есть трудности.
Я попробовал его решение, но оно не сработало - я решил опубликовать свой полный код вместе с его решением
У меня есть пользовательский слой Keras, который я хочу вернуть, указав c вывод из указанных c входов. Я не хочу, чтобы он был обучаемым.
Слой должен сделать следующее
if input = [1,0] then output = 1
if input = [0,1] then output = 0
Вот код лямбда-слоя для этого:
input_tensor = Input(shape=(n_hots,))
def custom_layer_1(tensor):
if tensor == [1,0]:
resp_1 = np.array([1,],dtype=np.int32)
k_resp_1 = backend.variable(value=resp_1)
return k_resp_1
elif tensor == [0,1]:
resp_0 = np.array([0,],dtype=np.int32)
k_resp_0 = backend.variable(value=resp_0)
return k_resp_0
else:
resp_e = np.array([-1,])
k_resp_e = backend.variable(value=resp_e)
return k_resp_e
print(tensor.shape)
layer_one = keras.layers.Lambda(custom_layer_1,output_shape = (None,))(input_tensor)
_model = Model(inputs=input_tensor, outputs = layer_one)
Когда я соответствую своей модели, она всегда вычисляет -1, несмотря на входные данные.
Вот как выглядит модель:
Layer (type) Output Shape Param #
=================================================================
input_1 (InputLayer) (None, 2) 0
_________________________________________________________________
lambda_1 (Lambda) (None, None) 0
=================================================================
Total params: 0
Trainable params: 0
Non-trainable params: 0
Вот полный код модели:
import numpy as np
from keras.models import Model
from keras import layers
from keras import Input
from keras import backend
import keras
from keras import models
import tensorflow as tf
# Generate the datasets:
n_obs = 1000
n_hots = 2
obs_mat = np.zeros((n_obs,n_hots),dtype=np.int32)
resp_mat = np.zeros((n_obs,1),dtype=np.int32)
# which position in the array should be "hot" ?
hot_locs = np.random.randint(n_hots, size=n_obs)
# set the bits:
for row,loc in zip(np.arange(n_obs),hot_locs):
obs_mat[row,loc] = 1
for idx in np.arange(n_obs):
if( (obs_mat[idx,:]==[1,0]).all() == True ):
resp_mat[idx] = 1
if( (obs_mat[idx,:]==[0,1]).all() == True ):
resp_mat[idx] = 0
# test data:
test_suite = np.identity(n_hots)
# Build the network
input_tensor = Input(shape=(n_hots,))
def custom_layer_1(tensor):
if tensor == [1,0]:
resp_1 = np.array([1,],dtype=np.int32)
k_resp_1 = backend.variable(value=resp_1)
return k_resp_1
elif tensor == [0,1]:
resp_0 = np.array([0,],dtype=np.int32)
k_resp_0 = backend.variable(value=resp_0)
return k_resp_0
else:
resp_e = np.array([-1,])
k_resp_e = backend.variable(value=resp_e)
return k_resp_e
print(tensor.shape)
layer_one = keras.layers.Lambda(custom_layer_1,output_shape = (None,))(input_tensor)
_model = Model(inputs=input_tensor, outputs = layer_one)
# compile
_model.compile(optimizer="adam",loss='mse')
#train (even thought there's nothing to train)
history_mdl = _model.fit(obs_mat,resp_mat,verbose=True,batch_size = 100,epochs = 10)
# test
_model.predict(test_suite)
# outputs: array([-1., -1.], dtype=float32)
test = np.array([1,0])
test = test.reshape(1,2)
_model.predict(test,verbose=True)
# outputs: -1
Это похоже на довольно простые вещи, почему не работает? Спасибо