原型网络tensorflow2代码(有bug)

代码主要是根据原型网络tensorflow1代码改的

源代码地址是https://github.com/sudharsan13296/Hands-On-Meta-Learning-With-Python/tree/master/03.%20Prototypical%20Networks%20and%20its%20Variants

所用数据集链接如下:

链接:https://pan.baidu.com/s/1Tp1KCq5oNv-2tq9Rso4lYw 
提取码:r94v 
 

import os 
import glob 
from PIL import Image 
import numpy as np 
import tensorflow as tf
from tensorflow.keras import models
from tensorflow.keras.layers import (Conv2D,Flatten,MaxPool2D,Dense,BatchNormalization,
                                     Dropout,Activation,Input,GlobalAveragePooling2D)

# GPU相关设置
os.environ["CUDA_VISIBLE_DEVICES"] = "0"
# 设置GPU按需增长
config = tf.compat.v1.ConfigProto()
config.gpu_options.allow_growth = True
sess = tf.compat.v1.Session(config=config)


root_dir = 'data/'

train_split_path = os.path.join(root_dir, 'splits', 'train.txt') 
with open(train_split_path, 'r') as train_split: 
    train_classes = [line.rstrip() for line in train_split.readlines()] 
    
#类的数量
no_of_classes = len(train_classes) 
#print(no_of_classes)  4112
#数据集中每类样本的数量
num_examples = 20 
#图像宽度
img_width = 28 
#图像高度
img_height = 28 
channels = 1 


#所需要一次训练类的数量
num_way = 50 

#支撑集中每个类的样本数量
num_shot = 5 
#查询集中查询点的数量
num_query = 1 



train_dataset = np.zeros([no_of_classes, num_examples, img_height,img_width], dtype=np.float32)

for label, name in enumerate(train_classes): 
    alphabet, character, rotation = name.split('/') 
    rotation = float(rotation[3:]) 
    img_dir = os.path.join(root_dir, 'data', alphabet, character) 
    img_files = sorted(glob.glob(os.path.join(img_dir, '*.png'))) 
    for index,img_file in enumerate(img_files):
        values = 1. - np.array(Image.open(img_file).rotate(rotation).resize((img_width,img_height)), np.float32, copy=False) 
        train_dataset[label, index] = values

print(train_dataset.shape)
#(4112, 20, 28, 28)


#一个卷积块
def convolution_block(Data_Input,conv_filter,conv_stride, name='conv'): 
    conv = Conv2D(filters = conv_filter,kernel_size = 3,strides = conv_stride,padding = "same",
                 kernel_initializer = tf.keras.initializers.glorot_uniform(seed = 1))(Data_Input)
    conv = MaxPool2D(pool_size = 2,strides = 2,padding = "valid")(conv)
    conv = BatchNormalization()(conv)
    conv = Activation("relu")(conv)
    return conv 

#卷积块堆叠提取特征向量
def get_embeddings(Data_Input,conv_filter,conv_stride = 1,reuse=False,remodel=1): 
    net = convolution_block(Data_Input,conv_filter[0],conv_stride)
    net = convolution_block(net,conv_filter[1], conv_stride) 
    net = convolution_block(net,conv_filter[2], conv_stride) 
    net = convolution_block(net,conv_filter[3], conv_stride) 
    net = Flatten(name = "Faltten")(net)
    
    net = models.Model(Data_Input,net) 
    net.summary()
    return net 

    
    
#定义了嵌入的网络架构
Data_Input = Input((28,28,1))
conv_filter = [1024,512,256,128]
net = get_embeddings(Data_Input,conv_filter)



#定义距离函数(欧氏距离)
def distance(a, b):
    N, D = a.shape[0], a.shape[1]
    M = b.shape[0]
    a = tf.tile(tf.expand_dims(a, axis=1), (1, M, 1))
    b = tf.tile(tf.expand_dims(b, axis=0), (N, 1, 1))
    result = tf.reduce_mean(tf.square(a - b), axis=2)
    # result = tf.convert_to_tensor(result, dtype=tf.float32)
    return result


    
loss = tf.keras.metrics.Mean(name='loss')
accuracy = tf.keras.metrics.SparseCategoricalAccuracy(name='accuracy')

# test_loss = tf.keras.metrics.Mean(name='test_loss')
# test_accuracy = tf.keras.metrics.SparseCategoricalAccuracy(name='test_accuracy')


loss_object = tf.keras.losses.CategoricalCrossentropy()

optimizer = tf.keras.optimizers.Adam()

num_epochs = 5 
num_episodes = 10
for epoch in range(num_epochs): 
    loss.reset_states()
    accuracy.reset_states()
    #test_loss.reset_states()
    #test_accuracy.reset_states()
    
    for episode in range(num_episodes): 
        #选择 50 个类
        episodic_classes = np.random.permutation(no_of_classes)[:num_way] 
        #(50,5,28,28)
        support = np.zeros([num_way, num_shot, img_height, img_width], dtype=np.float32) 
        #(50,5,28,28)
        
        #改为(50,1,28,28)
        query = np.zeros([num_way, num_query, img_height, img_width], dtype=np.float32) 
        
        # label = np.zeros([1,num_way],dtype=np.int64)
        #循环遍历随机打乱的类(已经取了前50个)
        for index, class_ in enumerate(episodic_classes): 
            #每个类总共含有20张照片,随机打乱顺序,然后挑选6个
            selected = np.random.permutation(num_examples)[:num_shot + num_query] 
            #前5个点用于生成支持集
            support[index] = train_dataset[class_, selected[:num_shot]] 
            
            #每个类 1 个查询点
            query[index] = train_dataset[class_, selected[num_shot:]] 
            
        
        # #最后一个维度进行扩张
        # support = np.expand_dims(support, axis=-1) 
        
        # 去除多余维度,再进行扩张
        query = np.squeeze(query)
        query = np.expand_dims(query, axis=-1)
        
        # 将标签变为独热编码,去除多余维度
        labels = np.tile(np.arange(num_way)[:, np.newaxis], (1,num_query)).astype(np.uint8)
        labels = tf.one_hot(labels,50)
        labels = np.squeeze(labels)
        
        # print(support.shape)  (50, 5, 28, 28, 1)
        # print(query.shape)    (50, 28, 28, 1)
        # print(labels.shape)   (50, 50)
        print(len(support))
        
        # 创建类原型
        support_set_embeddings = np.zeros([num_way,conv_filter[3]],dtype = np.float32)
        
        for i in range(len(support)):
            support_set = np.squeeze(support[i,:,:,:])
            support_set = np.expand_dims(support_set, axis=-1) 
            support_set_ = net(support_set)
            # print(support_set_)
            
            support_set_embeddings[i] = tf.reduce_mean(support_set_,axis = 0)
            
        support_set_embeddings = tf.convert_to_tensor(support_set_embeddings, dtype=tf.float32)
        print(support_set_embeddings.shape)
        
        
        
        
        
        # 查询集得到特征
        query_set = net(query)
        # query_set = tf.convert_to_tensor(query_set, dtype=tf.float32)
        # query_set = np.array(query_set,dtype=np.float32)
        # print(query_set.shape)
        
        
        
        # 计算距离
        # Distance = distance(support_set_embeddings,query_set)
        # Distance = tf.transpose(Distance)
        # print(type(Distance))
        
        for i in range(num_way):
            # Distance = tf.nn.softmax(Distance)
            with tf.GradientTape() as tape:
                Distance = distance(support_set_embeddings,query_set)
                Distance = tf.transpose(Distance)
                Distance = tf.nn.softmax(Distance)
                predictions = Distance[i]
                loss = loss_object(labels[i],predictions)
                print(loss.numpy())
            gradients = tape.gradient(loss, net.trainable_variables)
            optimizer.apply_gradients(zip(gradients, net.trainable_variables))
        
            loss(loss)
            accuracy(label, predictions)
        
        
        if (episode+1) % 20 == 0: 
            print('Epoch {} : Episode {} : Loss: {}, Accuracy: {}'.format(epoch+1, episode+1, loss.result(), accuracy.result()*100))

报错如下:

 

ValueError: No gradients provided for any variable: ['conv2d/kernel:0', 
'conv2d/bias:0', 'batch_normalization/gamma:0', 'batch_normalization/beta:0', 
'conv2d_1/kernel:0', 'conv2d_1/bias:0', 'batch_normalization_1/gamma:0', 
'batch_normalization_1/beta:0', 'conv2d_2/kernel:0', 'conv2d_2/bias:0', 
'batch_normalization_2/gamma:0', 'batch_normalization_2/beta:0', 'conv2d_3/kernel:0', 
'conv2d_3/bias:0', 'batch_normalization_3/gamma:0', 'batch_normalization_3/beta:0'].

 

深度学习小白,实在不知道错误原因是啥,要是哪位大佬需要用到,可以改改试试,能指正一下就十分感谢啦!

  • 2
    点赞
  • 7
    收藏
    觉得还不错? 一键收藏
  • 6
    评论
### 回答1: TensorFlow 2.0是Google开发的一款开源机器学习框架,它是TensorFlow的最新版本。相对于早期版本,TensorFlow 2.0更加易用,具有更好的性能和更好的可维护性。TensorFlow 2.0提供了Keras API的全面支持,使得构建神经网络变得更加容易和快速。此外,TensorFlow 2.0还提供了Eager Execution模式,这意味着可以在Python环境下进行实时计算和调试,而不需要像以前一样需要构建计算图。总之,TensorFlow 2.0是一个非常强大的机器学习框架,可以帮助开发者更加高效地构建和训练模型。 ### 回答2: TensorFlow是一个开源的人工智能框架,它是由Google开发并发布的。TensorFlow 2是TensorFlow的第二个重要版本,并且在原有版本的基础上进行了许多改进和优化。 TensorFlow 2 有很多新的特性和功能。首先,它引入了Keras的高级API作为默认的API。这样做使得TensorFlow变得更加易用和直观,并且可以方便地进行快速原型设计和模型迭代。 其次,TensorFlow 2可以进行动态计算图和静态计算图的混合运行。这意味着可以根据需要选择使用静态计算图(在编译时优化)或者动态计算图(在运行时优化)来加快计算速度。 另外,TensorFlow 2还引入了Eager Execution机制。这种机制允许用户即时地运行代码并获取结果,而无需进行繁琐的图构建和会话管理。 TensorFlow 2还具有更好的可移植性和可部署性。用户可以将模型轻松地导出到不同的设备和平台上,并在其他环境中重新加载和运行模型。 最后,TensorFlow 2还提供了更多的工具和函数来支持模型的开发和调试。例如,TensorBoard可以可视化模型的训练过程和性能指标,tf.data可以高效地加载和预处理数据。 总而言之,TensorFlow 2是一个功能强大且易用的深度学习框架,它不仅提供了高级API和各种工具,还具有高度的可移植性和可扩展性。无论是研究人员还是开发者,都可以使用TensorFlow 2来更加轻松地开发和部署自己的机器学习模型。 ### 回答3: TensorFlow 2是谷歌开发的一种开源的深度学习框架。它是TensorFlow的第二个主要版本,旨在提供更直观、更易用的编程体验,以支持广泛的机器学习和深度学习任务。 TensorFlow 2的最大变化是引入了动态图机制。与TensorFlow 1相比,动态图允许用户更自由地定义和修改模型结构,无需预先定义计算图。这使得开发和调试更加简单和灵活,尤其对于初学者来说更容易上手。 此外,TensorFlow 2还内置了一些高级功能,如Keras API。Keras是一个流行的深度学习框架,它以简洁易懂的接口和模块化设计而闻名。TensorFlow 2将Keras作为其封装的一部分,使得构建和训练神经网络模型更加简单和高效。 在功能方面,TensorFlow 2支持多种数据类型、多种硬件平台和多种运行环境。可以使用CPU、GPU或TPU等不同硬件来加速模型训练和推理。此外,TensorFlow 2提供了丰富的工具、库和扩展,使其能够支持各种深度学习任务,如图像处理、自然语言处理和推荐系统等。 总而言之,TensorFlow 2是一个强大且易用的深度学习框架,它在设计上注重简单性和灵活性。无论是初学者还是专业人士,都可以利用TensorFlow 2来构建、训练和部署各种复杂的机器学习和深度学习模型。

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 6
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值