1

我想构建子类tf.keras.Model并希望看到具有summary功能的模型结构。但它不起作用。以下是我的代码:

import tensorflow as tf

class MyModel(tf.keras.Model):
    def __init__(self):
        super(MyModel, self).__init__()
        self.conv1 = tf.keras.layers.Conv2D(32, 3, activation='relu')
        self.flatten = tf.keras.layers.Flatten()
        self.d1 = tf.keras.layers.Dense(128, activation='relu')
        self.d2 = tf.keras.layers.Dense(10, activation='softmax')

    def call(self, x):
        x = self.conv1(x)
        x = self.flatten(x)
        x = self.d1(x)
        return self.d2(x)

model = MyModel()
model.summary()

错误:

ValueError:此模型尚未构建。首先通过调用build()或调用fit()一些数据来构建模型,或者 input_shape在第一层中指定一个参数以进行自动构建。

4

3 回答 3

3

您需要调用每一层一次来推断形状,然后调用build()模型tf.keras.Model的输入形状作为参数的方法:

import tensorflow as tf
import numpy as np

class MyModel(tf.keras.Model):
    def __init__(self):
        super(MyModel, self).__init__()
        self.conv1 = tf.keras.layers.Conv2D(32, 3, activation='relu')
        self.flatten = tf.keras.layers.Flatten()
        self.d1 = tf.keras.layers.Dense(128, activation='relu')
        self.d2 = tf.keras.layers.Dense(10, activation='softmax')
        x = np.random.normal(size=(1, 32, 32, 3))
        x = tf.convert_to_tensor(x)
        _ = self.call(x)

    def call(self, x):
        x = self.conv1(x)
        x = self.flatten(x)
        x = self.d1(x)
        return self.d2(x)

model = MyModel()
model.build((32, 32, 3))
model.summary()
_________________________________________________________________
Layer (type)                 Output Shape              Param #   
=================================================================
conv2d (Conv2D)              multiple                  896       
_________________________________________________________________
flatten (Flatten)            multiple                  0         
_________________________________________________________________
dense (Dense)                multiple                  3686528   
_________________________________________________________________
dense_1 (Dense)              multiple                  1290      
=================================================================
Total params: 3,688,714
Trainable params: 3,688,714
Non-trainable params: 0
_________________________________________________________________


于 2019-04-15T11:46:40.603 回答
1

此处列出了更好的解决方案。您需要提供一个模型方法来显式地推断模型。

import tensorflow as tf
from tensorflow.keras.layers import Input

class MyModel(tf.keras.Model):
    def __init__(self):
        super().__init__()
        self.dense = tf.keras.layers.Dense(1)

    def call(self, inputs, **kwargs):
        return self.dense(inputs)

    def model(self):
        x = Input(shape=(1))
        return Model(inputs=[x], outputs=self.call(x))

MyModel().model().summary()
于 2019-12-21T10:59:31.783 回答
1

编辑@Vlad的答案以避免此错误ValueError: Input 0 of layer conv2d_10 is incompatible with the layer: : expected min_ndim=4, found ndim=3. Full shape received: (32, 32, 3)

将此行更改为

model.build((32, 32, 3 ))

到:

model.build((None, 32, 32, 3 ))

最终代码:

class MyModel(tf.keras.Model):
    def __init__(self):
        super(MyModel, self).__init__()
        self.conv1 = tf.keras.layers.Conv2D(32, 3, activation='relu')
        self.flatten = tf.keras.layers.Flatten()
        self.d1 = tf.keras.layers.Dense(128, activation='relu')
        self.d2 = tf.keras.layers.Dense(10, activation='softmax')
        x = np.random.normal(size=(1, 32, 32, 3))
        x = tf.convert_to_tensor(x)
        _ = self.call(x)

    def call(self, x):
        x = self.conv1(x)
        x = self.flatten(x)
        x = self.d1(x)
        return self.d2(x)

model = MyModel()
model.build((None, 32, 32, 3 ))
model.summary()

于 2021-05-25T16:27:00.447 回答