You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

PyTorch线性回归报错:张量无需梯度且无grad_fn的解决方法

PyTorch线性回归梯度清零报错解决方案

问题概述

编写PyTorch线性回归程序时,手动更新权重、偏置并清零梯度后,程序仅运行一轮就触发报错:RuntimeError: element 0 of tensors does not require grad and does not have a grad_fn。

错误原因

问题出在权重与偏置的更新逻辑:
在with torch.no_grad()代码块中,使用w = w - w.grad * 1e-5和b = b - b.grad * 1e-5的赋值方式,会生成全新的张量对象。新的w和b不再保留原张量的requires_grad=True属性,也没有梯度追踪所需的grad_fn。第二轮循环执行loss.backward()时,无法对这些普通张量进行反向传播,从而触发报错。

修正方案

需对原张量进行原地修改,保持张量对象不变的同时保留梯度追踪属性:

  1. 用原地减法操作替代赋值操作,比如w -= w.grad * 1e-5或w.sub_(w.grad * 1e-5)
  2. 梯度清零可使用w.grad.zero_()(原地清零,复用内存更高效)或w.grad = None

完整修正代码

import torch

# 示例输入与目标张量(实际使用时替换为自己的数据)
inputs_t = torch.randn(10, 3)
targets_t = torch.randn(10, 2)

# weights and biases
w = torch.randn(2,3, requires_grad=True)
b = torch.randn(2, requires_grad=True)
print(w.dtype, b.dtype)

# a linear function
def model(x):
  return x @ w.t() + b

# loss function
def mse(t1, t2):
  diff = (t1-t2)**2
  return torch.mean(diff)

# do this in a loop
for _ in range(100):
  preds = model(inputs_t)
  loss = mse(targets_t, preds)
  loss.backward()
  # print(loss)
  print(w.grad, b.grad)
  print("==============")
  with torch.no_grad():
    # 原地更新权重和偏置,避免创建新张量
    w -= w.grad * 1e-5
    b -= b.grad * 1e-5
    # 原地清零梯度
    w.grad.zero_()
    b.grad.zero_()

额外说明

  • with torch.no_grad()的作用是临时禁用梯度计算,避免更新操作被追踪,这部分逻辑是正确的
  • 若使用w.grad = None清零梯度,后续反向传播时PyTorch会重新创建梯度张量,功能上与zero_()一致,但zero_()内存复用效率更高

内容的提问来源于stack exchange,提问作者jodh singh

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.06.19 17:05:15