使用CNTK后端的Keras:编写自定义图层

时间:2017-06-26 16:25:13

标签: python keras cntk

我正在尝试在Keras中编写一个自定义图层来复制论文中提出的特定架构。该层没有可训练的重量。我相信这可能是相关的,因为没有必要扩展类Layer。

我正在使用CNTK后端,但我正在尝试将代码保持为尽可能后端不可知,所以我依赖于keras.backend中定义的接口,而不是直接使用CNTK。

现在我只想尝试一个小例子。示例如下:

import numpy as np

from scipy.misc import imread
from keras import backend as K

im = imread('test.bmp')

#I'm extending a grayscale image to behave as a color image
ex_im = np.empty([im.shape[0],im.shape[1],3])

ex_im[:,:,0] = im
ex_im[:,:,1] = im
ex_im[:,:,2] = im

conv_filter = K.ones([3,3,ex_im.shape[2],ex_im.shape[2]])
x = K.conv2d(ex_im,conv_filter,padding='same')

但是,此代码会导致以下错误:

  

RuntimeError:卷积当前需要主操作数   动态轴

CNTK要求卷积的输入具有动态轴,否则它会将输入的第一个维度解释为批量大小。所以我试着用占位符使轴动态化(我能找到的唯一方法):

import numpy as np

from scipy.misc import imread
from keras import backend as K

im = imread('test.bmp')

ex_im = np.empty([1,im.shape[0],im.shape[1],3])

ex_im[0,:,:,0] = im
ex_im[0,:,:,1] = im
ex_im[0,:,:,2] = im

place = K.placeholder(shape=((None,) + ex_im.shape[1:]))

conv_filter = K.ones([3,3,ex_im.shape[3],ex_im.shape[3]])
x = K.conv2d(place,conv_filter,padding='same')

图像现在是一个图像数组,基本上是批量大小为1。

这可以正常工作。但是,我无法弄清楚如何将输入提供给占位符以测试我的代码。 eval()不接受任何参数,并且似乎没有办法将输入作为参数传递给评估。

如果没有占位符,有没有办法做到这一点?或者将输入提供给占位符的方法?我做了一些根本错误的事情,应该走另一条道路吗?

我应该补充一点,我真的想避免被锁定在后端,所以任何解决方案都应该是后端不可知的。

1 个答案:

答案 0 :(得分:0)

对于使用自定义图层,您没有定义张量,让Keras为您完成。只需创建图层,将给予图层的内容已经是一个合适的张量:

images = np.ones((1,50,50,3))

def myFunc(x):
    conv_filter = K.ones([3,3,3,3])
    return K.conv2d(x,conv_filter,padding='same')

inp = Input((50,50,3))
out = Lambda(myFunc, output_shape=(50,50,3))(inp)

model = Model(inp,out)
print(model.predict(images))
相关问题