# 回顾多层感知机
import torch
from torch import nn
from torch.nn import functional as F
# nn.Sequential定义了一种特殊的Module
net=nn.Sequential(nn.Linear(20,256),nn.ReLU(),nn.Linear(256,10))
X=torch.rand(2,20)
net(X)
tensor([[-0.0206, -0.2242,  0.0583,  0.0661, -0.0224,  0.1897,  0.0905, -0.0934,
          0.0057, -0.1244],
        [ 0.0024, -0.2259,  0.0205,  0.1134,  0.0568,  0.0990,  0.3586,  0.0122,
          0.0602, -0.1546]], grad_fn=<AddmmBackward0>)
# 自定义网络
# !任何层或者神经网络都是块Module的子类
class MLP(nn.Module):
    '''
    神经网络是块(nn.Module)的子类
    '''
    def __init__(self):
        '''
        使用层自定义网络
        '''
        super().__init__()
        self.hidden=nn.Linear(20,256)
        self.out=nn.Linear(256,10)
    
    def forward(self,X):
        '''
        定义前向传播如何运算
        '''
        return self.out(F.relu(self.hidden(X)))

net=MLP()
net(X)
tensor([[-0.0719,  0.0567, -0.1176,  0.0573,  0.0871, -0.0618, -0.3144,  0.0601,
          0.0517, -0.0355],
        [-0.0563, -0.0485, -0.0900,  0.1496, -0.0129, -0.2652, -0.1559, -0.0092,
          0.0009, -0.1086]], grad_fn=<AddmmBackward0>)
# 自定义顺序网络
class MySequential(nn.Module):
    '''
    神经网络是块(nn.Module)的子类
    实现nn.Sequential()
    '''
    def __init__(self,*args):
        '''
        将层放入self._modules
        :param *args 列表入参 神经网络层
        '''
        super().__init__()
        # block 层
        for block in args:
            self._modules[block]=block
    
    def forward(self,X):
        '''
        为self._modules的每层赋值
        '''
        # 遍历层,和输入顺序一致
        for block in self._modules.values():
            # 输出层的输出作为下一层的输入
            X=block(X)
        return X

net=MySequential(nn.Linear(20,256),nn.ReLU(),nn.Linear(256,10))
net(X)
tensor([[ 0.1151, -0.2679, -0.1595,  0.1520,  0.0295,  0.0650, -0.0557,  0.3886,
          0.0172, -0.0907],
        [ 0.0779, -0.3375, -0.1760,  0.1571,  0.0889,  0.0351,  0.0729,  0.2392,
         -0.0437, -0.0138]], grad_fn=<AddmmBackward0>)
# 自定义固定隐藏层网络
class FixedHiddenMLP(nn.Module):
    '''
    隐藏层被固定,两次调用同1个隐藏层
    '''
    def __init__(self):
        super().__init__()
        # 随机初始化权重,不参与梯度计算
        self.rand_weight=torch.rand((20,20),requires_grad=False)
        self.linear=nn.Linear(20,20)
    
    def forward(self,X):
        '''
        在正向传播中执行代码
        '''
        # 调用第1次
        X=self.linear(X)
        # 自行计算转换函数
        # torch.mm(a,b) 矩阵乘法,数学矩阵乘法
        # +1是偏置
        X=F.relu(torch.mm(X,self.rand_weight)+1)
        # 调用第2次
        X=self.linear(X)
        while X.abs().sum()>1:
            X/=2
        return X.sum()

net=FixedHiddenMLP()
net(X)
tensor(-0.0769, grad_fn=<SumBackward0>)
# 自定义嵌套网络
class NestMLP(nn.Module):
    def __init__(self):
        super().__init__()
        self.net=nn.Sequential(nn.Linear(20,64),nn.ReLU(),
                              nn.Linear(64,32),nn.ReLU())
        self.linear=nn.Linear(32,16)
    
    def forward(self,X):
        return self.linear(self.net(X))

chimera=nn.Sequential(NestMLP(),nn.Linear(16,20),FixedHiddenMLP())
chimera(X)
tensor(0.1118, grad_fn=<SumBackward0>)
Logo

腾讯云面向开发者汇聚海量精品云计算使用和开发经验,营造开放的云计算技术生态圈。

更多推荐