我正在尝试实现本文所述的较小版本的SegNet(https://arxiv.org/pdf/1511.00561.pdf),但我正在尝试针对检测边缘进行定制

资料集:
我正在使用BSDS500边界数据集,我对图像进行了裁剪和旋转,因此其尺寸为320x480x3,而不是321x481x3

输入形状,200个训练图像和100个验证图像:

x_train: (200, 320, 480, 3)
x_val: (100, 320, 480, 3)
y_train: (200, 153600)
y_val: (100, 153600)


框架:
我正在使用带有tensorflow后端的keras

这些是我用于自定义池和解池层的功能:

def pool_argmax2D(x, pool_size=(2,2), strides=(2,2)):
    padding = 'SAME'
    pool_size = [1, pool_size[0], pool_size[1], 1]
    strides = [1, strides[0], strides[1], 1]
    ksize = [1, pool_size[0], pool_size[1], 1]
    output, argmax = tf.nn.max_pool_with_argmax(
        x,
        ksize = ksize,
        strides = strides,
        padding = padding
    )

    return [output, argmax]


def unpool2D(pool, argmax, ksize=(2,2)):
    with tf.variable_scope("unpool"):
        input_shape =  tf.shape(pool)
        output_shape = [input_shape[0],
                        input_shape[1] * ksize[0],
                        input_shape[2] * ksize[1],
                        input_shape[3]]

        flat_input_size = tf.cumprod(input_shape)[-1]
        flat_output_shape = tf.cast([output_shape[0],
                            output_shape[1] * output_shape[2] * output_shape[3]], tf.int64)

        pool_ = tf.reshape(pool, [flat_input_size])
        batch_range = tf.reshape(tf.range(tf.cast(output_shape[0], tf.int64), dtype=tf.int64),
                                shape=[input_shape[0], 1, 1, 1])

        b = tf.ones_like(argmax) * batch_range
        b = tf.reshape(b, [flat_input_size, 1])

        ind_ = tf.reshape(argmax, [flat_input_size, 1]) % flat_output_shape[1]
        ind_ = tf.concat([b, ind_], 1)
        ret = tf.scatter_nd(ind_, pool_, shape=flat_output_shape)
        ret = tf.reshape(ret, output_shape)
        return ret


这是该模型的代码:

batch_size = 4
kernel = 3
pool_size=(2,2)
img_shape = (320,480,3)


inputs = Input(shape=img_shape, name='main_input')

conv_1 = Conv2D(32, (kernel, kernel), padding="same")(inputs)
conv_1 = BatchNormalization()(conv_1)
conv_1 = Activation("relu")(conv_1)
conv_2 = Conv2D(32, (kernel, kernel), padding="same")(conv_1)
conv_2 = BatchNormalization()(conv_2)
conv_2 = Activation("relu")(conv_2)

pool_1, mask_1 = Lambda(pool_argmax2D, arguments={'pool_size': pool_size, 'strides': pool_size})(conv_2)

conv_3 = Conv2D(64, (kernel, kernel), padding="same")(pool_1)
conv_3 = BatchNormalization()(conv_3)
conv_3 = Activation("relu")(conv_3)
conv_4 = Conv2D(64, (kernel, kernel), padding="same")(conv_3)
conv_4 = BatchNormalization()(conv_4)
conv_4 = Activation("relu")(conv_4)

pool_2, mask_2 = Lambda(pool_argmax2D, arguments={'pool_size': pool_size, 'strides': pool_size})(conv_4)

conv_5 = Conv2D(64, (kernel, kernel), padding="same")(pool_2)
conv_5 = BatchNormalization()(conv_5)
conv_5 = Activation("relu")(conv_5)

unpool_1 = Lambda(unpool2D, output_shape = (160,240,64), arguments={'ksize':pool_size, 'argmax': mask_2})(conv_5)

conv_6 = Conv2D(64, (kernel, kernel), padding="same")(unpool_1)
conv_6 = BatchNormalization()(conv_6)
conv_6 = Activation("relu")(conv_6)
conv_7 = Conv2D(64, (kernel, kernel), padding="same")(conv_6)
conv_7 = BatchNormalization()(conv_7)
conv_7 = Activation("relu")(conv_7)

unpool_2 = Lambda(unpool2D, output_shape = (320,480,64), arguments={'ksize':pool_size, 'argmax': mask_1})(conv_7)

conv_8 = Conv2D(32, (kernel, kernel), padding="same")(unpool_2)
conv_8 = BatchNormalization()(conv_8)
conv_8 = Activation("relu")(conv_8)
conv_9 = Conv2D(32, (kernel, kernel), padding="same")(conv_8)
conv_9 = BatchNormalization()(conv_9)
conv_9 = Activation("relu")(conv_9)

conv_10 = Conv2D(1, (1, 1), padding="same")(conv_9)
conv_10 = BatchNormalization()(conv_10)

flatten_1 = Flatten()(conv_10)

outputs = Activation('softmax')(flatten_1)

model = Model(inputs=inputs, outputs=outputs)


运行时,模型可以正确编译:

model.compile(optimizer='adam', loss='mean_absolute_error', metrics=['accuracy'])
model.summary()

_________________________________________________________________
Layer (type)                 Output Shape              Param #
=================================================================
main_input (InputLayer)      (None, 320, 480, 3)       0
_________________________________________________________________
conv2d_1 (Conv2D)            (None, 320, 480, 32)      896
_________________________________________________________________
batch_normalization_1 (Batch (None, 320, 480, 32)      128
_________________________________________________________________
activation_1 (Activation)    (None, 320, 480, 32)      0
_________________________________________________________________
conv2d_2 (Conv2D)            (None, 320, 480, 32)      9248
_________________________________________________________________
batch_normalization_2 (Batch (None, 320, 480, 32)      128
_________________________________________________________________
activation_2 (Activation)    (None, 320, 480, 32)      0
_________________________________________________________________
lambda_1 (Lambda)            [(None, 160, 240, 32), (N 0
_________________________________________________________________
conv2d_3 (Conv2D)            (None, 160, 240, 64)      18496
_________________________________________________________________
batch_normalization_3 (Batch (None, 160, 240, 64)      256
_________________________________________________________________
activation_3 (Activation)    (None, 160, 240, 64)      0
_________________________________________________________________
conv2d_4 (Conv2D)            (None, 160, 240, 64)      36928
_________________________________________________________________
batch_normalization_4 (Batch (None, 160, 240, 64)      256
_________________________________________________________________
activation_4 (Activation)    (None, 160, 240, 64)      0
_________________________________________________________________
lambda_2 (Lambda)            [(None, 80, 120, 64), (No 0
_________________________________________________________________
conv2d_5 (Conv2D)            (None, 80, 120, 64)       36928
_________________________________________________________________
batch_normalization_5 (Batch (None, 80, 120, 64)       256
_________________________________________________________________
activation_5 (Activation)    (None, 80, 120, 64)       0
_________________________________________________________________
lambda_3 (Lambda)            (None, 160, 240, 64)      0
_________________________________________________________________
conv2d_6 (Conv2D)            (None, 160, 240, 64)      36928
_________________________________________________________________
batch_normalization_6 (Batch (None, 160, 240, 64)      256
_________________________________________________________________
activation_6 (Activation)    (None, 160, 240, 64)      0
_________________________________________________________________
conv2d_7 (Conv2D)            (None, 160, 240, 64)      36928
_________________________________________________________________
batch_normalization_7 (Batch (None, 160, 240, 64)      256
_________________________________________________________________
activation_7 (Activation)    (None, 160, 240, 64)      0
_________________________________________________________________
lambda_4 (Lambda)            (None, 320, 480, 64)      0
_________________________________________________________________
conv2d_8 (Conv2D)            (None, 320, 480, 32)      18464
_________________________________________________________________
batch_normalization_8 (Batch (None, 320, 480, 32)      128
_________________________________________________________________
activation_8 (Activation)    (None, 320, 480, 32)      0
_________________________________________________________________
conv2d_9 (Conv2D)            (None, 320, 480, 32)      9248
_________________________________________________________________
batch_normalization_9 (Batch (None, 320, 480, 32)      128
_________________________________________________________________
activation_9 (Activation)    (None, 320, 480, 32)      0
_________________________________________________________________
conv2d_10 (Conv2D)           (None, 320, 480, 1)       33
_________________________________________________________________
batch_normalization_10 (Batc (None, 320, 480, 1)       4
_________________________________________________________________
flatten_1 (Flatten)          (None, 153600)            0
_________________________________________________________________
activation_10 (Activation)   (None, 153600)            0
=================================================================
Total params: 205,893
Trainable params: 204,995
Non-trainable params: 898
_________________________________________________________________


但是,当尝试拟合模型时

history = model.fit(x=x_train, y=y_train, batch_size=batch_size, epochs=3, verbose=2, validation_data=(x_val,y_val))


我遇到此错误:

InvalidArgumentError: Input to reshape is a tensor with 4915200 values, but the requested shape has 9830400
     [[{{node lambda_4/unpool/Reshape_3}} = Reshape[T=DT_INT64, Tshape=DT_INT32, _device="/job:localhost/replica:0/task:0/device:GPU:0"](lambda_1/MaxPoolWithArgmax:1, lambda_4/unpool/Reshape_2/shape)]]
     [[{{node lambda_4/unpool/strided_slice_6/_515}} = _Recv[client_terminated=false, recv_device="/job:localhost/replica:0/task:0/device:CPU:0", send_device="/job:localhost/replica:0/task:0/device:GPU:0", send_device_incarnation=1, tensor_name="edge_1479_lambda_4/unpool/strided_slice_6", tensor_type=DT_INT64, _device="/job:localhost/replica:0/task:0/device:CPU:0"]()]]


我仔细检查了每一层之后的所有形状,这是我所期望的。我还测试了样本张量上的池化/解池功能,它们产生了预期的输出。我在这里做错了什么?

我一直在努力解决此问题,我们将不胜感激!

最佳答案

发现了问题,mask_1具有32个通道,而unpool_2尝试使用64个通道重塑输出。我只是重新整理了东西,所以深度排成一行。

07-24 09:53