Day 34:GPU训练与类的call方法

CPU性能基准测试

首先回顾昨天在CPU上的训练结果。使用鸢尾花数据集训练多层感知机,20000个epochs的训练时间为19.09秒。这为我们的对比分析提供了重要的基准线。

通过代码了解一下测试环境的CPU配置:

python 复制代码
import wmi
c = wmi.WMI()
processors = c.Win32_Processor()

for processor in processors:
    print(f"CPU 型号: {processor.Name}")
    print(f"核心数: {processor.NumberOfCores}")  
    print(f"线程数: {processor.NumberOfLogicalProcessors}")

# 输出:12th Gen Intel(R) Core(TM) i7-1255U
# 核心数: 10,线程数: 12

这是我的Intel第12代处理器,采用混合架构设计,结合了性能核心和能效核心,在处理小规模任务时具有良好的单核性能。

GPU训练环境配置

将训练迁移到GPU需要理解PyTorch的设备管理机制。核心概念是所有参与计算的张量和模型必须位于同一设备上:

python 复制代码
import torch

# 检测GPU环境
device = torch.device("cuda:0" if torch.cuda.is_available() else "cpu")
print(f"使用设备: {device}")

# 数据迁移到GPU
X_train = torch.FloatTensor(X_train).to(device)
y_train = torch.LongTensor(y_train).to(device)

# 模型迁移到GPU  
model = MLP().to(device)

这里需要注意.to(device)方法的行为差异:对于张量会返回新的副本,对于模型则直接修改原对象的参数位置。

意外的性能对比结果

运行相同的训练代码后,得到了比较意外的结果:

  • CPU训练时间:19.09秒
  • GPU训练时间:21.23秒

GPU居然比CPU更慢,但是跟据我们的经验GPU擅长并行运算,进行深度学习等科学计算相比CPU更有优势,训练速度应该更快。

GPU性能劣势的根本原因

GPU在小规模任务上表现不佳主要源于三个开销:

数据传输开销 是最主要的瓶颈。每次GPU计算都需要CPU内存到GPU显存的数据传输,更关键的是代码中的loss.item()操作会在每个epoch都进行GPU到CPU的同步传输:

python 复制代码
for epoch in range(num_epochs):
    outputs = model(X_train)
    loss = criterion(outputs, y_train)
    
    optimizer.zero_grad()
    loss.backward()  
    optimizer.step()
    
    losses.append(loss.item())  # 这里触发GPU->CPU传输!

对于20000个epochs,这种频繁的数据同步累积了大量开销。

核心启动开销是第二个因素。GPU的每个操作都需要启动计算核心,当实际计算量很小时,启动开销在总时间中占比显著。

计算资源浪费是第三个问题。鸢尾花数据集只有150个样本,无法充分利用GPU的大量并行计算单元。

性能优化实验验证

为了验证数据传输开销的影响,进行了对照实验,减少不必要的GPU-CPU同步操作:

python 复制代码
# 优化版本:减少数据传输频率
for epoch in range(num_epochs):
    outputs = model(X_train)
    loss = criterion(outputs, y_train)
    
    optimizer.zero_grad()
    loss.backward()
    optimizer.step()
    
    # 只在打印时才进行数据传输
    if (epoch + 1) % 100 == 0:
        print(f'Epoch [{epoch+1}/{num_epochs}], Loss: {loss.item():.4f}')

优化后的GPU训练时间降至14.86秒,接近CPU性能。这清晰地证明了数据传输开销的重大影响。

进一步的实验显示,记录频率与性能的关系并非简单的线性关系,这涉及GPU异步执行的复杂机制。

GPU优势的发挥条件

GPU的真正优势在于处理大规模并行计算任务。当满足以下条件时,GPU的性能优势才会显现:

处理包含数万张图片的大型数据集时,数据传输开销被大量计算掩盖。训练具有数百万参数的深度网络时,复杂的矩阵运算能充分利用GPU的并行架构。使用较大的批量处理时,能够填满GPU的计算单元。

简单来说,只有当计算量足够大时,GPU的并行优势才能超越各种固定开销。

PyTorch调用机制解析

python 复制代码
class MLP(nn.Module):
    def __init__(self):
        super(MLP, self).__init__()
        self.fc1 = nn.Linear(4, 10)  # 创建对象
        
    def forward(self, x):
        out = self.fc1(x)  # 像函数一样调用对象
        return out

这里self.fc1是一个对象,但可以像函数一样调用。这是因为nn.Module实现了__call__方法,当我们调用self.fc1(x)时,实际执行的是self.fc1.__call__(x),进而调用forward方法完成计算。

这种设计保证了接口的一致性,让所有PyTorch组件都能以统一方式调用。

@浙大疏锦行

相关推荐
叫我:松哥5 分钟前
基于Python的实习僧招聘数据采集与可视化分析,使用matplotlib进行可视化
开发语言·数据库·python·课程设计·matplotlib·文本挖掘
站大爷IP7 分钟前
Django模型开发全解析:字段、元数据与继承的实战指南
python
赵英英俊10 分钟前
Python day37
人工智能·python·深度学习
山烛2 小时前
OpenCV 图像处理基础操作指南(一)
图像处理·人工智能·python·opencv·计算机视觉
ScilogyHunter2 小时前
线性代数中矩阵的基本运算运算
线性代数·机器学习·矩阵
xw33734095643 小时前
scikit-learn工具介绍
python·机器学习·scikit-learn
TDengine (老段)4 小时前
TDengine 中 TDgpt 的模型评估工具
大数据·数据库·机器学习·ai·时序数据库·tdengine·涛思数据
中等生4 小时前
Python的隐形枷锁:GIL如何"绑架"了你的多线程梦想
后端·python
电商数据girl4 小时前
关于私域电商网站,接入电商API数据接口示例
运维·开发语言·网络·python·json·php