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

Jupyter Lab GPU运行异常:代码报错且nvidia-smi显示GPU闲置

问题:PyTorch模型未实际调用GPU且设备不匹配报错

Jupyter Lab显示正在使用GPU,但nvidia-smi显示GPU处于闲置状态;运行GPU密集型代码时,两块GPU利用率均为0%,进程列表无对应脚本,说明GPU未被实际调用。

通过PyTorch检测设备的代码及输出如下:

import torch

# 显示PyTorch版本
print(torch.__version__)
# 检查CUDA是否可用
print('Is CUDA available?', torch.cuda.is_available())

输出:

1.13.1+cu117
Is CUDA available? True

核心Net类代码如下:

class Net(nn.Module):
    device = torch.device("cuda") # 手动添加的设备定义
    def __init__(self, n_vocab, embedding_dim, hidden_dim, dropout=0.2):
        super(Net, self).__init__()

        self.embedding_dim = embedding_dim
        self.hidden_dim = hidden_dim # dim = dimension
        
        embedding_dim.to(device) # 手动添加的代码
        self.embeddings = nn.Embedding(n_vocab, embedding_dim)

        # LSTM层 (input_size, hidden_size)
        self.lstm = nn.LSTM(embedding_dim, hidden_dim, dropout=dropout)

        # 全连接层,将隐藏状态映射到输出
        self.hidden2out = nn.Linear(hidden_dim, n_vocab)

    def forward(self, seq_in):
        seq_in.to(device) # 手动添加的代码
        embeddings = self.embeddings(seq_in.t())

        lstm_out, _ = self.lstm(embeddings)
        ht = lstm_out[-1]

        out = self.hidden2out(ht)

        return out

代码运行时在embeddings = self.embeddings(seq_in.t())行抛出RuntimeError:

RuntimeError: Expected all tensors to be on the same device, but found at least two devices, cuda:0 and cpu! (when checking argument for argument index in method wrapper__index_select)


解决方案

错误根源在于模型参数与输入Tensor的设备不匹配,同时存在几处无效的设备操作,具体修改如下:

修改后的Net类代码

import torch
import torch.nn as nn

class Net(nn.Module):
    def __init__(self, n_vocab, embedding_dim, hidden_dim, dropout=0.2):
        super(Net, self).__init__()
        # 定义设备,增加CPU fallback逻辑
        self.device = torch.device("cuda" if torch.cuda.is_available() else "cpu")
        
        self.embedding_dim = embedding_dim
        self.hidden_dim = hidden_dim
        
        # 定义模型层
        self.embeddings = nn.Embedding(n_vocab, embedding_dim)
        self.lstm = nn.LSTM(embedding_dim, hidden_dim, dropout=dropout)
        self.hidden2out = nn.Linear(hidden_dim, n_vocab)
        
        # 将所有模型参数移动到指定设备
        self.to(self.device)

    def forward(self, seq_in):
        # 将输入Tensor移动到模型所在设备,必须重新赋值(to()默认不原地修改)
        seq_in = seq_in.to(self.device)
        # 转置后传入Embedding层
        embeddings = self.embeddings(seq_in.t())
        
        lstm_out, _ = self.lstm(embeddings)
        ht = lstm_out[-1]
        
        out = self.hidden2out(ht)
        return out

关键修改点说明

  • 移除无效的embedding_dim.to(device):embedding_dim是整数,不是Tensor,to()方法仅对Tensor和Module有效,这行代码完全没用。
  • 类属性device改为实例属性self.device:避免类属性共享导致的潜在问题,同时增加CPU fallback,确保无GPU环境也能运行。
  • 添加self.to(self.device):在初始化时将所有模型层(Embedding、LSTM、Linear)的参数统一移动到GPU,这是模型调用GPU的核心步骤。
  • 修改seq_in.to(device)为seq_in = seq_in.to(self.device):to()方法默认返回新的Tensor,原Tensor仍在CPU上,必须接收返回值才能让输入Tensor真正移动到GPU。

验证步骤

实例化模型后,可通过以下代码确认模型参数是否已在GPU上:

# 替换为你的实际参数值
model = Net(n_vocab=1000, embedding_dim=128, hidden_dim=256)
print(next(model.parameters()).device)  # 正常输出应为 cuda:0

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.07.31 13:45:15