• 4、神经网络的模块化接口torch.nn


    本博客参考 http://studyai.com/pytorch-1.4/beginner/blitz/neural_networks_tutorial.html + 《PyTorch入门与实践》

    torch.nn最核心的类是nn.Module,一个 nn.Module 包含若干 layers, 和一个方法 forward(input), 该方法返回 output 。

    自定义的网络类需要继承nn.Module,其构造函数里必须执行一次父类构造函数。

    网络中拥有可学习的参数的层要放在构造函数中,不拥有的随意。

    torch.nn 仅支持 mini-batches。 整个 torch.nn package 仅支持以样本的 mini-batch 作为输入,而不支持单个样本作为输入。

    例如, nn.Conv2d 将接受一个shape为 nSamples nChannels Height Width 的 4D Tensor 作为输入。

    如果你有一个单样本, 请使用 input.unsqueeze(0) 将batch_size设为1(即nSamples),nChannels Height Width 

    神经网络的训练步骤:

    1、定义一个神经网络
    2、处理输入并backward
    3、计算损失(度量 网络的输出 离 我们期望的正确输出 还有多远)
    4、使用优化器(优化方法)更新网络的权重和参数

    #代码中的数据参考上图
    ########################################### 1、定义一个神经网络
    import torch.nn as nn import torch.nn.functional as F class Net(nn.Module): #定义网络类,继承自nn.Module def __init__(self): #类的构造函数 super(Net,self).__init__() #执行一次父类的构造函数(硬性要求),等价于 nn.Module.__init__(self) ## 卷积层 self.conv1=nn.Conv2d(1,6,5) #输入图像 1 个通道, 6 个输出通道, 5x5 方形卷积核 self.conv2=nn.Conv2d(6,16,5) #上层的6作为此层的输入,输出16通道,5x5 ## 仿射层/全连接层,y=Wx+b self.fc1=nn.Linear(16*5*5,120) self.fc2=nn.Linear(120,84) self.fc3=nn.Linear(84,10) def forward(self, x): #卷积→激活→池化 # 最大池化的窗口大小(2, 2) x = F.max_pool2d(F.relu(self.conv1(x)), (2, 2)) # 如果池化窗口是方形的,你只需要指定单个数字 x = F.max_pool2d(F.relu(self.conv2(x)), 2) #-1代表自适应,reshape x = x.view(x.size()[0],-1) x = F.relu(self.fc1(x)) x = F.relu(self.fc2(x)) x = self.fc3(x) return x net = Net() print(net)

    只要nn.Module子类中定义了forward函数,backward函数就会被自动实现。下图输出的结果:

    # 参数个数
    print(len(list(net.parameters())))
    # 输出参数
    for name in net.parameters():
        print(name)
    # 参数名,每个参数的大小
    for name,param in net.named_parameters():
        print(name,":",param.size())

     

    ########################################### 2、处理输入并backward
    #
    尝试一个 32x32 的随机输入,这个网络(LeNet)期望的输入尺寸是 32x32 input=t.randn(1,1,32,32) out=net(input) #使用已设定的网络,1个输入,输出10个 print(out.size()) print(out) #反向传播前,所有参数的梯度清零 net.zero_grad() out.backward(t.randn(1, 10))

    ########################################### 3、计算损失(度量 网络的输出 离 我们期望的正确输出 还有多远)
    output=net(input)
    target=t.randn(10) #一个虚拟的目标值, 为了举例子,不要太在意
    target=target.view(1,-1) # 使其具有与输出相同的shape
    criterion=nn.MSELoss() #损失函数中的一种:平均平方误差(mean-squared error),nn.CrossEntropyLoss交叉熵损失
    
    loss=criterion(output,target)
    print(loss)

    net.zero_grad() #把net中所有可学习参数的梯度清零
    print("反向传播之前conv1.bias的梯度")
    print(net.conv1.bias.grad)
    loss.backward() #反向传播,该图会动态生成并自动微分,也会自动计算图中参数的导数
    print("反向传播之后conv1.bias的梯度")
    print(net.conv1.bias.grad)

    ########################################### 4、使用优化器(优化方法)更新网络的权重和参数
    import torch.optim as optim
    optimizer=optim.SGD(net.parameters(),lr=0.01) #新建优化器,指定要调整的参数和学习率。SGD随机梯度下降法
    #先梯度清零
    optimizer.zero_grad() #等效 net.zero_grad()
    #计算损失
    output=net(input)
    loss=criterion(output,target)
    #反向传播
    loss.backward()
    #更新参数
    optimizer.step()
  • 相关阅读:
    C#代码中函数调用相关问题
    C#语言编写代码时常用的三大循环
    c#语言中的类型转换
    tesseract_vs2015工具包使用
    Halcon除法
    halcon批量读取图片
    halcon分离路径名称
    Halcon旋转图片的研究
    关于Haclon使用GPU加速的代码实例
    OpenCV代码:画出轮廓的外接矩形,和中心点
  • 原文地址:https://www.cnblogs.com/xixixing/p/12626987.html
Copyright © 2020-2023  润新知