我正在Keras的一个片段中工作,在这里我有两个顺序模型,需要将它们合并到第三个模型中,这是我的最终模型。该代码段是使用Keras版本构建的,允许使用Merge方法,因此现在我尝试用axis = 0
的连接方法替换它,因此其行为与Merge()相同。尽管进行了所有这些修改,但我仍收到以下堆栈跟踪作为输出:
Traceback (most recent call last):
File ".\CaptionGenerator.py", line 738, in <module>
caption.BeamPredictor('image.PNG')
File ".\CaptionGenerator.py", line 485, in BeamPredictor
self.SetNeuralNetworksWithoutApi()
File ".\CaptionGenerator.py", line 433, in SetNeuralNetworksWithoutApi
Activation('softmax')
File "D:\Anaconda\lib\site-packages\keras\engine\sequential.py", line 92, in __init__
self.add(layer)
File "D:\Anaconda\lib\site-packages\keras\engine\sequential.py", line 131, in add
'Found: ' + str(layer))
TypeError: The added layer must be an instance of class Layer. Found: Tensor("concatenate_1/concat:0", shape=(?, 40, 300), dtype=float32)
代码段代码为:
def SetNeuralNetworksWithoutApi(self):
embedding_size = 300
image_model = Sequential([
Dense(embedding_size, input_shape=(2048,), activation='relu'),
RepeatVector(self.MaxCaptionLength)
])
caption_model = Sequential([
Embedding(self.numberOfWords, embedding_size, input_length=self.MaxCaptionLength),
LSTM(256, return_sequences=True),
TimeDistributed(Dense(300))
])
image_in = Input(shape=(2048,))
caption_in = Input(shape=(self.numberOfWords,))
merged = concatenate([image_model(image_in), caption_model(caption_in)])
latent = Bidirectional(LSTM(256, return_sequences=False))(merged)
out = Dense(self.numberOfWords, activation='softmax')(latent)
self.softmaxModel = Model([image_in, caption_in], out)
self.softmaxModel.compile(loss='categorical_crossentropy', optimizer=RMSprop(), metrics=['accuracy'])
self.softmaxModel.summary()
我不明白为什么我的concatenate()结果不应该是Layer类的实例的原因,考虑到从函数返回的对象中没有layer属性,根据文档,该对象是张量。有什么方法可以解决这个问题而无需切换到API?谢谢。
答案 0 :(得分:1)
至少对于最终模型,您需要切换到functional API,因为Sequential
被设计为具有单个输入,您将向其中强制输入2个张量。不上班。这是因为Sequential为其输入创建了一个占位符。类似于:
image_model = Sequential([
Dense(embedding_size, input_shape=(2048,), activation='relu'),
RepeatVector(self.MaxCaptionLength)
])
caption_model = Sequential([
Embedding(self.numberOfWords, embedding_size, input_length=self.MaxCaptionLength),
LSTM(256, return_sequences=True),
TimeDistributed(Dense(300))
])
image_in = Input(shape=(2048,))
caption_in = Input(shape=(MaxCaptionLength, numberOfWords))
merged = concatenate([image_model(image_in), caption_model(caption_in)], axis=0)
latent = Bidirectional(LSTM(256, return_sequences=False))(merged)
out = Dense(self.numberOfWords, activation='softmax')(latent)
final_model = Model([image_in, caption_in], out)
final_model.compile(loss='categorical_crossentropy', optimizer=RMSprop(), metrics=['accuracy'])
final_model.summary()
您仍然可以将图像模型和标题模型保持分开,但是即使有一种解决方法可以将Sequential与2个输入连接起来,我也不建议这样做,因为这不是该API的预期用途。