11.22 深度学习-pytorch自动微分

自动微分模块torch.autograd负责自动计算张量操作的梯度,具有自动求导功能。自动微分模块是构成神经网络训练的必要模块,可以实现网络权重参数的更新,使得反向传播算法的实现变得简单而高效

import torch

1. **张量**

Torch中一切皆为张量,属性requires_grad决定是否对其进行梯度计算。默认是 False,如需计算梯度则设置为True。

2. **计算图**:

torch.autograd通过创建一个动态计算图来跟踪张量的操作,每个张量是计算图中的一个节点,节点之间的操作构成图的边。

3. **反向传播**

使用tensor.backward()方法执行反向传播,从而计算张量的梯度。这个过程会自动计算每个张量对损失函数的梯度。

4. **梯度**

计算得到的梯度通过tensor.grad访问,这些梯度用于优化模型参数,以最小化损失函数。

张量的梯度计算 导数值

使用tensor.backward() 求tensor的导数值 会先求 tensor的导函数 然后带入值 这个tensor 是关于另一个tensor的表达式 原来的tensor是一组数据浮点型 这个tensor是一个函数

创建 原来的tensor时 要设置 requires_grad=True 表示这个tensor要被用于求导 设置了之后 tensor每次参加运算都会被求导一次 吃性能

调用backward 后 原来的tensor 就有个grad属性 这个属性是 导数值

一个 标量映射成另一个标量 对这个映射的结果做反向传播 结果在原来 标量里面

def demo1():

t1= torch.tensor(7.0, requires_grad=True, dtype=torch.float32)

t2= t1**2 + 2 * t1 + 7

t2.backward()

print(t1.grad)

向量的梯度计算

映射的结果必须是一个标量才行 对映射进行一下处理让他为标量 比如求和 或者平均值

def demo2():

torch.manual_seed(666)

t1=torch.rand(20,4, requires_grad=True, dtype=torch.float32)

t2= t1**2 + 2 * t1 + 7

t2=t2.sum()

t2.backward()

print(t1.grad) # 返回的是原向量每一个元素的梯度 是一个跟原来向量size一样的tensor

多标量梯度计算 就是映射式子里面有两个未知数 两个变量tensor 就是求了一个偏导

两个变量就都有了grad

def demo3():

t1= torch.tensor(7.0, requires_grad=True, dtype=torch.float32)

t2= torch.tensor(5.0, requires_grad=True, dtype=torch.float32)

t3= t1**2 + 2 * t1 + 7+t2**2

t3.backward()

print(t1.grad)

print(t2.grad)

多向量也差不多不过要先 变为标量

理解 一个tensor 代表一个W tensor里面代表这个W的取值情况 ,然后当这些W取值的时候 Y应该也有个对应的值组成了一个数据集 有x和y的 这样就可以 算梯度了

y.backward()的时候 相当于把y 表达式的 导函数求出来存在y的一个属性里面 然后再把y表达式中的变量的值传进来计算导数 再返回给 变量的grad属性里面

def demo4():

torch.manual_seed(666)

t1=torch.rand(20,4, requires_grad=True, dtype=torch.float32)

torch.manual_seed(3)

t2=torch.rand(20,4, requires_grad=True, dtype=torch.float32)

t3= t1**2 + 2 * t1 + 7+t2**2

t3=t3.sum()

t3.backward()

print(t1.grad)

print(t2.grad)

梯度的上下文控制

梯度计算的上下文控制和设置对于管理计算图、内存消耗、以及计算效率至关重要。下面我们学习下Torch中与梯度计算相关的一些主要设置方式。

映射函数y的requires_grad默认为ture 不用的话占性能 可以手动关了

def demo4():

x=torch.rand(20,4, requires_grad=True, dtype=torch.float32)

使用with语法 torch.no_grad() 关闭梯度 with torch.no_grad(): 局部作用 再with里面所有的torch都没有requires_grad

with torch.no_grad():

y = x**2 + 2 * x + 3 # 没有梯度的y

print(y.requires_grad) # False

或者装饰器也可以

@torch.no_grad()

def test():

y = x**2 + 2 * x + 3 # 没有梯度的y

return y

全局设置 设置了之后后面代码全部都没有梯度了

torch.set_grad_enabled(False)

累积梯度 多次backward 的时候每次给变量返回的导数值 会累加起来 而不是覆盖 因为不管你怎么变y的表达式 都会给y里面的变量 返回个梯度 让他存起来

def demo5():

torch.manual_seed(666)

t1=torch.rand(20,4, requires_grad=True, dtype=torch.float32)

for x in range(3):

t2= t1**2 + 2 * t1 + 7

t2=t2.sum()

t2.backward()

print(t1.grad)

梯度清空 每次backward 把梯度清空了 tensor.grad.zero_()

def demo6():

torch.manual_seed(666)

t1=torch.rand(20,4, requires_grad=True, dtype=torch.float32)

for x in range(3):

t2= t1**2 + 2 * t1 + 7

t2=t2.sum()

if t1.grad != None:

t1.grad.zero_()

t2.backward()

print(t1.grad)

梯度更新 手动

def demo7():

定义初始W 学习率和 训练轮次

torch.manual_seed(666)

w1=torch.rand(3,3,3,requires_grad=True)

torch.manual_seed(6)

w2=torch.rand(3,3,3,requires_grad=True)

print(w1,w2)

lr=0.1

turn=100

开始训练 假设 均方差公式

for x in range(turn):

y=w1**2+w2**2+2*w1+2*w2+100

清空梯度

if w1.grad!=None:

w1.grad.zero_()

if w2.grad!=None:

w2.grad.zero_()

计算梯度

y=y.mean()

y.backward()

得到当前梯度

梯度更新 使用tensor.data

w1.data=w1.data-lr*w1.grad

w2.data=w1.data-lr*w2.grad

得到训练完后的 w值 可以保存 这个时候w有requires_grad=Ture 保存的时候 去掉用detach 下次使用 load出来

print(w1,w2)

torch.save(w1.detach(),"assets/w/w1.plt")

torch.save(w2.detach(),"assets/w/w2.plt")

注意事项

当requires_grad=True时,在调用numpy转换为ndarray时报错

使用detach()方法创建张量的叶子节点即可 tensor.detach().numpy()

detach() 就是原来 requires_grad=Flase的tensor 和原来的tensor 浅拷贝 改一个两个都变

def test():

torch.manual_seed(666)

w1=torch.rand(3,3,3,requires_grad=True)

print(w1)

w2=w1.detach()

print(w2)

w2[:,:,1]=100

print(w1)

print(w2)

if name=="main":

demo1()

demo2()

demo3()

demo4()

demo5()

demo6()

demo7()

test()

相关推荐
搞笑的秀儿14 分钟前
信息新技术
大数据·人工智能·物联网·云计算·区块链
阿里云大数据AI技术32 分钟前
OpenSearch 视频 RAG 实践
数据库·人工智能·llm
XMAIPC_Robot44 分钟前
基于ARM+FPGA的光栅尺精密位移加速度测试解决方案
arm开发·人工智能·fpga开发·自动化·边缘计算
加油吧zkf1 小时前
YOLO目标检测数据集类别:分类与应用
人工智能·计算机视觉·目标跟踪
Blossom.1181 小时前
机器学习在智能制造业中的应用:质量检测与设备故障预测
人工智能·深度学习·神经网络·机器学习·机器人·tensorflow·sklearn
天天扭码1 小时前
AI时代,前端如何处理大模型返回的多模态数据?
前端·人工智能·面试
难受啊马飞2.01 小时前
如何判断 AI 将优先自动化哪些任务?
运维·人工智能·ai·语言模型·程序员·大模型·大模型学习
顺丰同城前端技术团队2 小时前
掌握未来:构建专属领域的大模型与私有知识库——从部署到微调的全面指南
人工智能·deepseek
许泽宇的技术分享2 小时前
用.NET9+Blazor+Semantic Kernel,打造企业级AI知识库和智能体平台——AntSK深度解读
人工智能
烟锁池塘柳02 小时前
【深度学习】强化学习(Reinforcement Learning, RL)主流架构解析
人工智能·深度学习·机器学习