我正在尝试构建一个TensorFlow模型,该模型以3张图像作为输入,并为每个输入图像提供3个输出嵌入,并进一步希望继续训练。部分代码如下所示:
def tripler_trainer(input_shape=(112,112,3)):
anchor_input = layers.Input(shape=input_shape)
positive_input = layers.Input(shape=input_shape)
negative_input = layers.Input(shape=input_shape)
embedder = inner_model(act_func='relu', input_shape=(112,112,3) # return embedding of shape(1,128)
anchor_embedding = embedder(anchor_input)
positive_embedding = embedder(positive_input)
negative_embedding = embedder(negative_input)
outer_network = Model(inputs=(anchor_input, positive_input, negative_input),
outputs=(anchor_embedding, positive_embedding, negative_embedding))
return outer_network
def triplet_loss(triplets, margin=0.20):
triplet_loss = 0
anchor = triplets[0]
positive = triplets[1]
negative = triplets[2]
anchor = tf.math.l2_normalize(anchor, axis=None, epsilon=1e-12, name=None, dim=None)
positive = tf.math.l2_normalize(positive, axis=None, epsilon=1e-12, name=None, dim=None)
negative = tf.math.l2_normalize(negative, axis=None, epsilon=1e-12, name=None, dim=None)
# print(anchor)
anchor_pos_dist = tf.sqrt(tf.reduce_sum(tf.square(anchor - positive)))
anchor_neg_dist = tf.sqrt(tf.reduce_sum(tf.square(anchor - negative)))
if anchor_pos_dist <= anchor_neg_dist <= (anchor_pos_dist + margin):
triplet_loss = np.max(((anchor_pos_dist - anchor_neg_dist) + margin), 0)
return triplet_loss
epochs = 100
optimizer = tf.keras.optimizers.SGD(learning_rate=1e-3)
train_data_util_instance = TripletFormulator(data_path_dictionary=data_path, batch=4) # data path contains 3 subfolders containing images of different class
train_data_array_dict, data_count = train_data_util_instance.data_loader()
majority_class = max(data_count, key=data_count.get)
for epoch in range(epochs):
for majority_class_batch in train_data_array_dict[majority_class]:
train_batch_dict = {}
train_batch_dict['class A'] = next(iter(train_data_array_dict['A']))
train_batch_dict['class B'] = next(iter(train_data_array_dict['B']))
train_batch_dict['class C'] = majority_class_batch
train_triplets = train_data_util_instance.triplet_generator(train_batch_dict) # Batch of triplets. with each instance containing 3 images.
for triplets in train_triplets:
with tf.GradientTape() as tape:
logits = self.model([tf.reshape(triplets[0], [-1, 112, 112, 3]),
tf.reshape(triplets[1], [-1, 112, 112, 3]),
tf.reshape(triplets[2], [-1, 112, 112, 3])], training=True)
loss_value = triplet_loss(triplets=logits, alpha=0.2)
grads = tape.gradient(loss_value, self.model.trainable_weights)
optimizer.apply_gradients(zip(grads, self.model.trainable_weights))
当我尝试运行代码时,我得到以下错误:
File "C:/Users/G5205GK/Desktop/Working Dir/code/con_learning/main.py", line 35, in <module>
main()
File "C:/Users/G5205GK/Desktop/Working Dir/code/con_learning/main.py", line 31, in main
training_instance.train()
File "C:\Users\G5205GK\Desktop\Working Dir\code\con_learning\train.py", line 45, in train
grads = tape.gradient(loss_value, self.model.trainable_weights)
File "C:\Users\G5205GK\Anaconda3\envs\my_gpu_env\lib\site-packages\tensorflow\python\eager\backprop.py", line 1074, in gradient
flat_grad = imperative_grad.imperative_grad(
File "C:\Users\G5205GK\Anaconda3\envs\my_gpu_env\lib\site-packages\tensorflow\python\eager\imperative_grad.py", line 71, in imperative_grad
return pywrap_tfe.TFE_Py_TapeGradient(
AttributeError: 'numpy.float32' object has no attribute '_id'
任何一个请建议问题在哪里。也提供的代码,是简化堆栈溢出。所以它可能有语法问题。
此外,代码工作到线的损失计算.提前感谢.
1条答案
按热度按时间zf2sa74q1#
在计算模型的损失时,您应该使用Tensorflow操作。尝试将
np.max
替换为tf.math.reduce_max
: