Keras:是否有任何解决方法可以在不使用 Lamda 层的情况下拆分中间层的输出?

Keras: Is there any workaround to split the output of an intermediate layer without using Lamda layer?

说,我有一个 10x10x4 卷积层的中间输出,我需要将其分成 100 1x1x4 体积并对每个体积应用 softmax 以从网络获得 100 个输出。有什么方法可以不使用 Lambda 层来实现这一点吗? Lambda 层在这种情况下的问题是,这个简单的拆分任务在前向传递期间需要通过 lambda 层 100 次,这使得网络性能对于我的实际使用来说非常慢。请建议一种更快的方法。

编辑:在问这个问题之前,我已经尝试过 Softmax+Reshape 方法。使用这种方法,我会将一个 10x10x4 矩阵重塑为 100x4 张量,并使用 Reshape 作为输出。我真正需要的是一个具有 100 个不同输出的多输出网络。在我的应用程序中,不可能对 10x10 矩阵进行联合优化,但我通过使用具有 100 个不同输出的网络和 Lambda 层获得了很好的结果。

以下是我使用 Keras 函数式方法的代码片段 API:

使用 Lambda 层(慢,根据需要给出 100 个形状为 (None, 4) 的张量):

# Assume conv_output is output from a convolutional layer with shape (None, 10, 10,4)
preds = []
for i in range(10):
    for j in range(10):
        y = Lambda(lambda x, i,j: x[:, i, j,:],  arguments={'i': i,'j':j})(conv_output)
        preds.append(Activation('softmax',name='predictions_' + str(i*10+j))(y))

model = Model(inputs=img, outputs=preds, name='model')
model.compile(loss='categorical_crossentropy',
              optimizer=Adam(),
              metrics=['accuracy']

使用 Softmax+Reshape(速度快,但给出形状为 (None, 100, 4) 的张量)

# Assume conv_output is output from a convolutional layer with shape (None, 10, 10,4)
y = Softmax(name='softmax', axis=-1)(conv_output)
preds = Reshape([100, 4])(y)
model = Model(inputs=img, outputs=preds, name='model')
model.compile(loss='categorical_crossentropy',
              optimizer=Adam(),
              metrics=['accuracy']

我认为在第二种情况下不可能对 100 个输出中的每一个进行单独优化(可能可以将其视为学习联合分布,而我需要像第一种情况那样学习边缘案子)。请让我知道是否有任何方法可以更快地完成我在第一个代码片段中使用 Lambda 层所做的事情

您可以使用 Softmax 层并将轴参数设置为最后一个轴(即 -1)以在该轴上应用 softmax:

from keras.layers import Softmax

soft_out = Softmax(axis=-1)(conv_out)

请注意,axis 参数默认设置为 -1,因此您甚至可能不需要传递它。