这是定义模型的两种完全不同的方法。
Keras使用层的概念。每一行定义网络的完整层。具体来说,您所指的是Keras的功能API。其概念是将这样的层组合在一起:
inp = Input(shape=(28, 28, 1))
x = Conv2D((6,6), strides=(1,1), activation='relu')(inp)
# ... etc ...
x = Flatten()(x)
x = Dense(10, activation='softmax')(x)
model = Model(inputs=[inp], outputs=[x])
从未
现在,这只需要
model.compile(...)
然后你可以训练它通过
model.fit(...)
另一方面,张量流则稍微低一点。这意味着您已经手工定义了变量和操作。因此,要编写一个完全连接的层,您必须执行以下操作:
# Input placeholders
x = tf.placeholder(tf.float32, shape=(None, 28, 28, 1))
y = tf.placeholder(tf.float32, shape=(None, 10))
# Convolution layer
W1 = tf.Variable(tf.truncated_normal([6, 6, 1, 32], stddev=0.1))
b1 = tf.Variable(tf.constant(0.1, tf.float32, [32]))
z1 = tf.nn.conv2d(x_2d, W1, strides=[1, 1, 1, 1], padding='SAME') + b1
c1 = tf.nn.relu(z1)
# ... etc ...
# Flatten
flat = tf.reshape(p2, [-1, ...]) # need to calculate the ... by ourselves
# Dense
W3 = tf.Variable(tf.truncated_normal([..., 10], stddev=0.1)) # same size as before
b3 = tf.Variable(tf.constant(0.1, tf.float32, [10]))
fc1 = tf.nn.relu(tf.matmul(flat, W3) + b3)
model
这里必须通过
tf.Session
feed_dict
将数据提供给占位符。如果你感兴趣,你可以在网上找到几本指南。
TensorFlow有一种更友好、更容易的方法来定义和训练模型
老路
没有一层是
__call__
方法,也使其可调用。他们这样做是为了包装
call
您可以查看实现
here
class MyClass:
def __init__(self, param):
self.p = param
def call(self, x):
print(x)
如果你想写
c = MyClass(1)(3)
class MyClass:
def __init__(self, param):
self.p = param
def __call__(self, x):
print(x)
现在可以工作了。基本上,Keras是这样做的:
class MyClass:
def __init__(self, param):
self.p = param
def call(self, x):
print(x)
def __call__(self, x):
self.call(x)
方法和
包装您的方法将从Keras的基类继承。