明明tensorflow1x就没有学好,现在换了2,那就再从头学起叭
在自定义类模块打印遇到了各种bug,在此记录一下,也希望可以帮助到有需要的伙伴。
如果你自定义类代码写成如下格式
import tensorflow as tf
from tensorflow.keras.models import Model
class SAEModel(Model):
def __init__(self, input_shape, output_shape, hidden_shape=None):
# print("init")
# 隐藏层节点个数默认为输入层的3倍
if hidden_shape == None:
hidden_shape = 3 * input_shape
# 调用父类__init__()方法
super(SAEModel, self).__init__()
# 初始化模型使用的layer,layer_1为前述自定义layer
self.layer_1 = SAELayer(hidden_shape)
# layer_2为全连接层,采用sigmoid激活函数
# 每层在这里可以不考虑输入元素个数,但必须考虑输出元素个数
# 输入元素个数可以在call()函数中动态确定
self.layer_2 = layers.Dense(output_shape, activation=tf.nn.sigmoid)
def call(self, input_tensor, training=False):
# 输入数据
hidden = self.layer_1(input_tensor)
output = self.layer_2(hidden)
return output
那么会报错如下,提示你需要使用model.build(input_shape=)方法。但是!我这个input_shape参数我输入总是出现各种错误。
有时打印出来的模型框架也不理想,如下图
在多方搜索后,看到了某位大神的代码,然后修改自己代码,完美输出。
https://blog.csdn.net/qq_40642546/article/details/106622996
class MyLstm(tf.keras.Model):
def __init__(self, voca_len, out_len, max_len, batch_size, embedding_dim, unit_num, embed_matrix = None):
#==============================================
super().__init__()
# =============================================
self.voca_len = voca_len
self.out_len = out_len
self.max_len = max_len
self.batch_size = batch_size
self.embedding_dim = embedding_dim
self.unit_num = unit_num
self.embed_matrix = None
self.input_layer = Input(max_len,
name = 'inputs')
if self.embed_matrix == None:
self.embedding_layer = Embedding(input_dim = self.voca_len,
output_dim = self.embedding_dim,
input_length = self.max_len,
trainable = True,
name = 'embedding')
else:
self.embedding_layer = Embedding(input_dim = self.voca_len,
output_dim = self.embedding_dim,
weights = [self.embed_matrix],
input_length = self.max_len,
name = 'embedding')
self.lstm_layer = LSTM(units=self.unit_num,
activation = 'relu',
name = 'LSTM')
self.out_layer = Dense(units=self.out_len,
name = 'Train_out')
self.out = self.call(self.input_layer) # !!!!!
# ================================================
super().__init__(inputs=self.input_layer,
outputs=self.out)
#=================================================
def build(self):
self.is_graph_network = True
self.__init__graph_network(inputs=self.input_layer,
outputs = self.out)
def call(self, x, from_logits=False, training=True, mask=None):
embed_matrix = self.embedding_layer(x)
# print(embed_matrix)
lstm_output= self.lstm_layer(embed_matrix)
logits = self.out_layer(lstm_output)
if from_logits:
return logits
else:
return tf.nn.sigmoid(logits)
model = MyLstm(voca_len=394, out_len=504, max_len=29, embedding_dim=23, unit_num=100, batch_size=2)
model.summary()
关键的地方在上面的代码中做了注释,两次初始化很重要,至于为啥这么写。。。
emmmmm 我先会用叭