Pytorch学习记录(4) torch.nn.module的使用

Pytorch学习记录(4) torch.nn.module的使用

  1. torch.nn.module的定义:

torch.nn是专门为神经网络设计的模块化接口. nn构建于autograd之上,可以用来定义和运行神经网络。

nn.Module是nn中十分重要的类,包含网络各层的定义及forward方法。

在用户自定义神经网络时,需要继承自nn.Module类。

我们可以通过重写子类的__init__与forward函数,实现自己需要的神经网络以及向前传播函数。

具体相关函数的参数介绍可以参考Module — PyTorch 1.13 documentation

  1. torch.nn.module的简单使用:

在官网中,对于nn.module的代码介绍如下:


import torch.nn as nn
import torch.nn.functional as F

class Model(nn.Module):  # Model类继承自nn.Module
    def __init__(self):   # 构造函数
        super(Model, self).__init__()  # 在构造函数中要调用Module的构造函数
        self.conv1 = nn.Conv2d(1, 20, 5)  # 卷积操作
        self.conv2 = nn.Conv2d(20, 20, 5) # 卷积操作

    def forward(self, x): # 前向传播函数
        x = F.relu(self.conv1(x))  # 先卷积操作conv1,后非线性操作relu
        return F.relu(self.conv2(x))

在定义自己的神经网络时,可以通过以下的方法:

1)需要继承nn.Module类,并实现forward方法。继承nn.Module类之后,在构造函数中要调用Module的构造函数, super(Linear, self).init()

2)一般把网络中具有可学习参数的层放在构造函数__init__()中。

3)不具有可学习参数的层(如ReLU)可放在构造函数中,也可不放在构造函数中(而在forward中使用nn.functional来代替)。可学习参数放在构造函数中,并且通过nn.Parameter()使参数以parameters(一种tensor,默认是自动求导)的形式存在Module中,并且通过parameters()或者named_parameters()以迭代器的方式返回可学习参数。

4)只要在nn.Module中定义了forward函数,backward函数就会被自动实现(利用Autograd)。而且一般不是显式的调用forward(layer.forward), 而是layer(input), 会自执行forward().

5)在forward中可以使用任何Variable支持的函数,毕竟在整个pytorch构建的图中,是Varible在流动。还可以使用if, for, print, log等python语法。

  1. 构建一个简单的自定义层


import torch
import torchvision.datasets
from torch import nn
from torch.nn import Sequential, Conv2d, MaxPool2d, Flatten, Linear, CrossEntropyLoss
from torch.utils.data import DataLoader

# 加载数据集,转换成tensor类型
dataset = torchvision.datasets.CIFAR10(root="./data", train=False, download=True,
                                       transform=torchvision.transforms.ToTensor())
dataloader = DataLoader(dataset, batch_size=1)


# 创建网络
class Model(nn.Module):
    def __init__(self):
        super(Model, self).__init__()
        self.model1 = Sequential(
            Conv2d(3, 32, 5, padding=2),
            MaxPool2d(2),
            Conv2d(32, 32, 5, padding=2),
            MaxPool2d(2),
            Conv2d(32, 64, 5, padding=2),
            MaxPool2d(2),
            Flatten(),
            Linear(1024, 64),
            Linear(64, 10)
        )

    def forward(self, x):
        x = self.model1(x)
        return x


# 定义计算loss
loss = CrossEntropyLoss()

m = Model()
# 设置优化器
optim = torch.optim.SGD(m.parameters(), lr=0.01)

for epoch in range(20):
    running_loss = 0.0
    for data in dataloader:
        imgs, targets = data
        outputs = m(imgs)
        result_loss = loss(outputs, targets)  # 计算数据集经过神经网络后的输出和真实数据输出之间的误差
        optim.zero_grad()  # 梯度清零————要把网络模型当中每一个 调节 参数梯度 调为0,参数清零
        result_loss.backward()  # 反向传播求解梯度————调用存损失函数的反向传播,求出每个节点的梯度,
        optim.step()  # 更新权重参数————调用优化器,对每个参数进行调优,循环
        running_loss = running_loss + result_loss  # 对整体损失的求和

    print(running_loss)

PS:在机器学习中,优化器(optimizer)是一种用于更新模型参数以最小化训练误差的算法。它可以将损失函数的梯度作为输入,并根据该梯度调整模型参数的值。

先将梯度值归零,:optimizer.zero_grad();

然后反向传播计算得到每个参数的梯度值:loss.backward();

最后通过梯度下降执行一步参数更新:optimizer.step();

由于pytorch的动态计算图,当我们使用loss.backward()和opimizer.step()进行梯度下降更新参数的时候,梯度并不会自动清零。并且这两个操作是独立操作。

4. 总结

本文的实践说明了如何使用Module父类来拓展实现自定义模型、自定义层,我们发现二者有异曲同工之处,这也是pytorch如此受欢迎的原因之一了。

  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值