当前位置: 首页 > news >正文

郓城那家网站做的好好123上网主页

郓城那家网站做的好,好123上网主页,巩义网站建设优化公司,建行网点Pytorch 复习总结,仅供笔者使用,参考教材: 《动手学深度学习》Stanford University: Practical Machine Learning 本文主要内容为:Pytorch 深度学习计算。 本文先介绍了深度学习中自定义层和块的方法,然后介绍了一些…

Pytorch 复习总结,仅供笔者使用,参考教材:

  • 《动手学深度学习》
  • Stanford University: Practical Machine Learning

本文主要内容为:Pytorch 深度学习计算。

本文先介绍了深度学习中自定义层和块的方法,然后介绍了一些有关参数的方法。


Pytorch 语法汇总:

  • Pytorch 张量的常见运算、线性代数、高等数学、概率论 部分 见 Pytorch 复习总结1;
  • Pytorch 线性神经网络 部分 见 Pytorch 复习总结2;
  • Pytorch 多层感知机 部分 见 Pytorch 复习总结3;
  • Pytorch 深度学习计算 部分 见 Pytorch 复习总结4;
  • Pytorch 卷积神经网络 部分 见 Pytorch 复习总结5;
  • Pytorch 现代卷积神经网络 部分 见 Pytorch 复习总结6;

目录

  • 一. 自定义块
    • 1. 顺序块
    • 2. 自定义前向传播
    • 3. 嵌套块
  • 二. 自定义层
    • 1. 无参数层
    • 2. 有参数层
  • 三. 参数管理
    • 1. 参数访问
    • 2. 参数初始化
    • 3. 延后初始化
  • 四. 文件读写
    • 1. 加载和保存张量
    • 2. 加载和保存模型参数

层是神经网络的基本组成单元,如全连接层、卷积层、池化层等。块是由层组成的更大的功能单元,用于构建复杂的神经网络结构。块可以是一系列相互关联的层,形成一个功能完整的单元,也可以是一组层的重复模式,用于实现重复的结构。下图就是多个层组合成块形成的更大模型:
在这里插入图片描述

在实际应用中,经常会需要自定义层和块。

一. 自定义块

1. 顺序块

nn.Sequential 本质上就是一个顺序块,通过在块中实例化层来创建神经网络。 nn.Module 是 PyTorch 中用于构建神经网络模型的基类,nn.Sequential 和各种层都是继承自 Module,nn.Sequential 维护一个由多个层组成的有序列表,列表中的每个层连接在一起,将每个层的输出作为下一个层的输入。

如果想要自定义一个顺序块,必须要定义以下两个关键函数:

  1. 构造函数:将每个层按顺序逐个加入列表;
  2. 前向传播函数:将每一层按顺序传递给下一层;
import torch
from torch import nnclass MySequential(nn.Module):def __init__(self, *args):super().__init__()for idx, module in enumerate(args):self._modules[str(idx)] = moduledef forward(self, X):# self._modules的类型是OrderedDictfor block in self._modules.values():X = block(X)return Xnet = MySequential(nn.Linear(20, 256),nn.ReLU(),nn.Linear(256, 10)
)X = torch.rand(2, 20)
output = net(X)

上述示例代码中,定义 net 时会自动调用 __init__(self, *args) 函数,实例化 MySequential 对象;调用 net(X) 相当于 net.__call__(X),会自动调用模型类中定义的 forward() 函数,进行前向传播,每一层的传播本质上就是调用 block(X) 的过程。

2. 自定义前向传播

nn.Sequential 类将前向传播过程封装成函数,用户可以自由使用但没法修改传播细节。如果想要自定义前向传播过程中的细节,就需要自定义顺序块及 forward 函数,而不能仅仅依赖预定义的框架。

例如,需要一个计算函数 f ( x , w ) = c ⋅ w T x f(\bold x,\bold w)=c \cdot \bold w ^T \bold x f(x,w)=cwTx 的层,并且在传播过程中引入控制流。其中 x \bold x x 是输入, w \bold w w 是参数, c c c 是优化过程中不需要更新的指定常量。为此,定义 FixedHiddenMLP 类如下:

import torch
from torch import nn
from torch.nn import functional as Fclass FixedHiddenMLP(nn.Module):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):X = self.linear(X)X = F.relu(torch.mm(X, self.rand_weight) + 1)X = self.linear(X)          # 两个全连接层共享参数while X.abs().sum() > 1:    # 控制流X /= 2return X

3. 嵌套块

多个层可以组合成块,多个块还可以嵌套形成更大的模型:

import torch
from torch import nn
from torch.nn import functional as Fclass FixedHiddenMLP(nn.Module):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):X = self.linear(X)X = F.relu(torch.mm(X, self.rand_weight) + 1)X = self.linear(X)          # 两个全连接层共享参数while X.abs().sum() > 1:    # 控制流X /= 2return X.sum()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))net = nn.Sequential(NestMLP(), nn.Linear(16, 20), FixedHiddenMLP()
)X = torch.rand(2, 20)
output = net(X)

二. 自定义层

和自定义块一样,自定义层也需要实现构造函数和前向传播函数。

1. 无参数层

import torch
from torch import nnclass CenteredLayer(nn.Module):def __init__(self):super().__init__()def forward(self, X):return X - X.mean()net = nn.Sequential(nn.Linear(8, 128), CenteredLayer())
X = torch.rand(4, 8)
output = net(X)
print(output.mean())	# tensor(0., grad_fn=<MeanBackward0>)

2. 有参数层

import torch
from torch import nn
import torch.nn.functional as Fclass MyLinear(nn.Module):def __init__(self, in_units, out_units):super().__init__()self.weight = nn.Parameter(torch.randn(in_units, out_units))self.bias = nn.Parameter(torch.randn(out_units,))def forward(self, X):linear = torch.matmul(X, self.weight.data) + self.bias.datareturn F.relu(linear)net = nn.Sequential(MyLinear(64, 8), MyLinear(8, 1)
)
X = torch.rand(2, 64)
output = net(X)
print(output)       # tensor([[11.9497], [13.9729]])

三. 参数管理

在实验过程中,有时需要提取参数,以便检查或在其他环境中复用。本节将介绍参数的访问方法和参数的初始化。

1. 参数访问

  • net.state_dict() / net[i].state_dict():返回模型或某一层参数的状态字典;
  • net[i].weight.data / net[i].bias.data:返回某一层的权重 / 偏置参数;
  • net[i].weight.grad:返回某一层的权重参数的梯度属性。只有调用了 backward() 方法后才能访问到梯度值,否则为 None;
import torch
from torch import nnnet = nn.Sequential(nn.Linear(4, 8), nn.ReLU(), nn.Linear(8, 1))
X = torch.rand(size=(2, 4))
output = net(X)print(net.state_dict())
'''
OrderedDict([('0.weight', tensor([[ 0.2178, -0.3286,  0.4875, -0.0347],[-0.0415,  0.0009, -0.2038, -0.1813],[-0.2766, -0.4759, -0.3134, -0.2782],[ 0.4854,  0.0606,  0.1070,  0.0650],[-0.3908,  0.2412, -0.1348,  0.3921],[-0.3044, -0.0331, -0.1213, -0.1690],[-0.3875, -0.0117,  0.3195, -0.1748],[ 0.1840, -0.3502,  0.4253,  0.2789]])), ('0.bias', tensor([-0.2327, -0.0745,  0.4923, -0.1018,  0.0685,  0.4423, -0.2979,  0.1109])), ('2.weight', tensor([[ 0.1006,  0.2959, -0.1316, -0.2015,  0.2446, -0.0158,  0.2217, -0.2780]])), ('2.bias', tensor([0.2362]))])
'''
print(net[2].state_dict())
'''
OrderedDict([('weight', tensor([[ 0.1006,  0.2959, -0.1316, -0.2015,  0.2446, -0.0158,  0.2217, -0.2780]])), ('bias', tensor([0.2362]))])
'''
print(net[2].bias)
'''
Parameter containing:
tensor([0.2362], requires_grad=True)
'''
print(net[2].bias.data)
'''
tensor([0.2362])
'''

如果想一次性访问所有参数,可以使用 for 循环递归遍历:

import torch
from torch import nnnet = nn.Sequential(nn.Linear(4, 8), nn.ReLU(), nn.Linear(8, 1))
X = torch.rand(size=(2, 4))
output = net(X)print(*[(name, param.shape) for name, param in net[0].named_parameters()])
'''
('weight', torch.Size([8, 4])) ('bias', torch.Size([8]))
'''
print(*[(name, param.shape) for name, param in net.named_parameters()])
'''
('0.weight', torch.Size([8, 4])) ('0.bias', torch.Size([8])) ('2.weight', torch.Size([1, 8])) ('2.bias', torch.Size([1]))
'''

如果网络是由多个块相互嵌套的,可以按块索引后再访问参数:

import torch
from torch import nndef block1():return nn.Sequential(nn.Linear(4, 8), nn.ReLU(),nn.Linear(8, 4), nn.ReLU())def block2():net = nn.Sequential()for i in range(4):net.add_module(f'block {i}', block1())return netnet = nn.Sequential(block2(), nn.Linear(4, 1))
X = torch.rand(size=(2, 4))
output = net(X)print(net)
'''
Sequential((0): Sequential((block 0): Sequential((0): Linear(in_features=4, out_features=8, bias=True)(1): ReLU()(2): Linear(in_features=8, out_features=4, bias=True)(3): ReLU())(block 1): Sequential((0): Linear(in_features=4, out_features=8, bias=True)(1): ReLU()(2): Linear(in_features=8, out_features=4, bias=True)(3): ReLU())(block 2): Sequential((0): Linear(in_features=4, out_features=8, bias=True)(1): ReLU()(2): Linear(in_features=8, out_features=4, bias=True)(3): ReLU())(block 3): Sequential((0): Linear(in_features=4, out_features=8, bias=True)(1): ReLU()(2): Linear(in_features=8, out_features=4, bias=True)(3): ReLU()))(1): Linear(in_features=4, out_features=1, bias=True)
)
'''
print(net[0][1][0].bias.data)
'''
tensor([-0.0083,  0.2490,  0.1794,  0.1927,  0.1797,  0.1156,  0.4409,  0.1320])
'''

2. 参数初始化

PyTorch 的 nn.init 模块提供了多种初始化方法:

  • nn.init.constant_(layer.weight, c):将权重参数初始化为指定的常量值;
  • nn.init.zeros_(layer.weight):将权重参数初始化为 0;
  • nn.init.ones_(layer.weight):将权重参数初始化为 1;
  • nn.init.uniform_(layer.weight, a, b):将权重参数按均匀分布初始化;
  • nn.init.xavier_uniform_(layer.weight)
  • nn.init.normal_(layer.weight, mean, std):将权重参数按正态分布初始化;
  • nn.init.orthogonal_(layer.weight):将权重参数初始化为正交矩阵;
  • nn.init.sparse_(layer.weight, sparsity, std):将权重参数初始化为稀疏矩阵;

初始化时,可以直接 net.apply(init_method) 初始化整个网络,也可以 net[i].apply(init_method) 初始化某一层:

import torch
from torch import nndef init_normal(m):if type(m) == nn.Linear:nn.init.normal_(m.weight, mean=0, std=0.01)nn.init.zeros_(m.bias)def init_constant(m):if type(m) == nn.Linear:nn.init.constant_(m.weight, 1)nn.init.zeros_(m.bias)net = nn.Sequential(nn.Linear(4, 8), nn.ReLU(), nn.Linear(8, 1))
X = torch.rand(size=(2, 4))
output = net(X)# net.apply(init_normal)
net[0].apply(init_normal)
net[2].apply(init_constant)

3. 延后初始化

有些情况下,无法提前判断网络的输入维度。为了代码能够继续运行,需要使用延后初始化,即直到数据第一次通过模型传递时,框架才会动态地推断出每个层的大小。由于 PyTorch 的延后初始化功能还处于开发阶段,API 和功能随时可能变化,下面只给出简单示例:

import torch
from torch import nnnet = nn.Sequential(nn.LazyLinear(256), nn.ReLU(), nn.LazyLinear(10))print(net)
'''
Sequential((0): LazyLinear(in_features=0, out_features=256, bias=True)(1): ReLU()(2): LazyLinear(in_features=0, out_features=10, bias=True)
)
'''X = torch.rand(2, 20)
net(X)
print(net)
'''
Sequential((0): Linear(in_features=20, out_features=256, bias=True)(1): ReLU()(2): Linear(in_features=256, out_features=10, bias=True)
)
'''

四. 文件读写

可以使用 loadsave 函数读写张量和模型参数。

1. 加载和保存张量

2. 加载和保存模型参数

http://www.qdjiajiao.com/news/11334.html

相关文章:

  • 上海由多少家网站建设公司百度推广怎么推广
  • 郑州网站制作免费谷歌搜索广告
  • wordpress与laravel鞍山seo优化
  • 网络服务器管理软件日喀则网站seo
  • html5 网站源码sem竞价
  • 长春做网站网站市场营销四大分析方法
  • 项目网站分析东莞企业网站设计公司
  • 网站页面和图片设计竞价托管开户
  • 新网$网站优化百度搜索网
  • 创业做网站开发南宁百度seo建议
  • 网站的建设与维护有什么作用好网站制作公司
  • 企业网站的设计与实现论文为企业推广
  • 公司做网站价格迅雷磁力链bt磁力种子
  • 武汉网络兼职网站建设淘宝关键词排名查询
  • 古典网站素材天津seo诊断技术
  • 网站开发源码交易链接
  • 做网站西安广告免费推广网
  • 广告策划方案范文seo工作流程图
  • wordpress用阿里云图床百度seo关键词排名推荐
  • 织梦后台如何做网站地图不屏蔽的国外搜索引擎
  • 屏蔽某网站怎么做网站维护是什么意思
  • 怎么做网站导航栏实事新闻热点
  • 服装公司logo设计某网站seo策划方案
  • 微网站和微信公共平台的区别优化落实疫情防控新十条
  • 一级av做爰片不卡免费网站网络营销的8个基本职能
  • 不是万维网的网站交换友链是什么意思
  • 网页游戏广告平台网站建设seo网站优化
  • sae 网站备案百度问答平台
  • 包头北京网站建设进入百度网首页
  • 做旅游宣传哪个网站好自媒体平台有哪些