这是一个简单的示例,在我尝试部署的网络中重现我的问题。
我有一个图像输入层(我需要维护),然后是一个密集层、Conv2D 层和一个密集层。
想法是输入是 10x10 图像,标签是 10x10 图像。受到我的代码和这个示例的启发。
import numpy as np
from keras.models import Model
from keras.layers import Input, Conv2D
#Building model
size=10
a = Input(shape=(size,size,1))
hidden = Dense(size)(a)
hidden = Conv2D(kernel_size = (3,3), filters = size*size, activation='relu', padding='same')(hidden)
outputs = Dense(size, activation='sigmoid')(hidden)
model = Model(inputs=a, outputs=outputs)
model.compile(loss='binary_crossentropy', optimizer='adam', metrics=['accuracy'])
#Create random data and accounting for 1 channel of data
n_images=55
data = np.random.randint(0,2,(n_images,size,size,1))
labels = np.random.randint(0,2,(n_images,size,size,1))
#Fit model
model.fit(data, labels, verbose=1, batch_size=10, epochs=20)
print(model.summary())
我收到以下错误:
ValueError: Error when checking target: expected dense_92 to have shape (10, 10, 10) but got array with shape (10, 10, 1)
如果我更改,我不会收到错误:
outputs = Dense(size, activation='sigmoid')(hidden)
与:
outputs = Dense(1, activation='sigmoid')(hidden)
不知道
Dense(1)
如何有效以及它如何允许10x10输出信号,如model.summary()
所示:
_________________________________________________________________
Layer (type) Output Shape Param #
=================================================================
input_26 (InputLayer) (None, 10, 10, 1) 0
_________________________________________________________________
dense_93 (Dense) (None, 10, 10, 10) 20
_________________________________________________________________
conv2d_9 (Conv2D) (None, 10, 10, 100) 9100
_________________________________________________________________
dense_94 (Dense) (None, 10, 10, 1) 101
=================================================================
Total params: 9,221
Trainable params: 9,221
Non-trainable params: 0
_________________________________________________________________
None
编辑(从旧评论中移走):
我想做的不是标准的。我有一组图像,对于每个图像,我想找到一个大小相同的二进制图像,如果 其像素值为1表示该特征存在于输入图像中
了解像素是否具有特征应该从局部信息(由卷积层提取)和全局信息中获取 密集层提取的信息。
嗯,根据您的评论:
我想做的不是标准的。我有一组图像和 每个图像我想找到一个相同大小的二值图像,如果 其像素值为1表示该特征存在于输入图像中
关于像素是否具有特征的见解应该来自 局部信息(由卷积层提取)和全局信息 密集层提取的信息。
我猜你正在寻找创建一个两分支模型,其中一个分支由卷积层组成,另一个分支只是一个或多个彼此之上的密集层(尽管,我应该提到,在我看来,一个卷积网络可以实现什么你正在寻找,因为池化层和卷积层的组合,然后可能是最后的一些上采样层以某种方式保留了本地和全局信息)。要定义这样的模型,您可以使用Keras功能API,如下所示:
from keras import models
from keras import layers
input_image = layers.Input(shape=(10, 10, 1))
# branch one: dense layers
b1 = layers.Flatten()(input_image)
b1 = layers.Dense(64, activation='relu')(b1)
b1_out = layers.Dense(32, activation='relu')(b1)
# branch two: conv + pooling layers
b2 = layers.Conv2D(32, (3,3), activation='relu')(input_image)
b2 = layers.MaxPooling2D((2,2))(b2)
b2 = layers.Conv2D(64, (3,3), activation='relu')(b2)
b2_out = layers.MaxPooling2D((2,2))(b2)
# merge two branches
flattened_b2 = layers.Flatten()(b2_out)
merged = layers.concatenate([b1_out, flattened_b2])
# add a final dense layer
output = layers.Dense(10*10, activation='sigmoid')(merged)
output = layers.Reshape((10,10))(output)
# create the model
model = models.Model(input_image, output)
model.compile(optimizer='rmsprop', loss='binary_crossentropy')
model.summary()
型号总结:
__________________________________________________________________________________________________
Layer (type) Output Shape Param # Connected to
==================================================================================================
input_1 (InputLayer) (None, 10, 10, 1) 0
__________________________________________________________________________________________________
conv2d_1 (Conv2D) (None, 8, 8, 32) 320 input_1[0][0]
__________________________________________________________________________________________________
max_pooling2d_1 (MaxPooling2D) (None, 4, 4, 32) 0 conv2d_1[0][0]
__________________________________________________________________________________________________
flatten_1 (Flatten) (None, 100) 0 input_1[0][0]
__________________________________________________________________________________________________
conv2d_2 (Conv2D) (None, 2, 2, 64) 18496 max_pooling2d_1[0][0]
__________________________________________________________________________________________________
dense_1 (Dense) (None, 64) 6464 flatten_1[0][0]
__________________________________________________________________________________________________
max_pooling2d_2 (MaxPooling2D) (None, 1, 1, 64) 0 conv2d_2[0][0]
__________________________________________________________________________________________________
dense_2 (Dense) (None, 32) 2080 dense_1[0][0]
__________________________________________________________________________________________________
flatten_2 (Flatten) (None, 64) 0 max_pooling2d_2[0][0]
__________________________________________________________________________________________________
concatenate_1 (Concatenate) (None, 96) 0 dense_2[0][0]
flatten_2[0][0]
__________________________________________________________________________________________________
dense_3 (Dense) (None, 100) 9700 concatenate_1[0][0]
__________________________________________________________________________________________________
reshape_1 (Reshape) (None, 10, 10) 0 dense_3[0][0]
==================================================================================================
Total params: 37,060
Trainable params: 37,060
Non-trainable params: 0
__________________________________________________________________________________________________
请注意,这是实现您正在寻找的目标的一种方法,它可能对特定问题和您正在处理的数据有效,也可能无效。您可以修改此模型(例如删除池化层或添加更密集的层)或完全使用具有不同类型层的另一种架构(例如上采样、conv2dtrans)以达到更好的精度。最后,您必须进行实验才能找到完美的解决方案。
编辑:
为了完整起见,这里介绍如何生成数据和拟合网络:
n_images=10
data = np.random.randint(0,2,(n_images,size,size,1))
labels = np.random.randint(0,2,(n_images,size,size,1))
model.fit(data, labels, verbose=1, batch_size=32, epochs=20)