1. 别急着下单新显卡:先搞懂训练慢的真正病灶在哪
“深度学习该租哪种GPU平台?训练速度慢,先别急着换显卡”——这句话我去年在实验室里听到了至少17遍。每次都是学生或刚入行的工程师盯着训练日志里那缓慢爬升的loss曲线,第一反应就是:“是不是显卡太弱了?赶紧租个A100!”结果花大价钱租了顶配云GPU,跑起来发现batch size一调大就OOM,数据加载瓶颈卡在CPU和磁盘IO上,GPU利用率常年徘徊在30%以下,钱花了,时间也耗了,问题却纹丝不动。
这背后不是硬件不行,而是对深度学习训练全流程的性能瓶颈缺乏系统性诊断意识。GPU只是整个数据-计算-通信链条中的一环,它再快,也救不了被慢吞吞读取的硬盘、被低效预处理拖垮的CPU、被不合理调度压垮的内存,更救不了那些写得像散文诗一样的PyTorch DataLoader。我见过太多人把“训练慢”这个症状,直接等同于“GPU差”,就像发烧了不查血常规,上来就开抗生素——治标不治本,还可能耽误正事。
所以这篇内容的核心,不是给你列一张“GPU租用平台排行榜”,而是带你亲手拆解训练流程,像一个老练的汽车修理工一样,用一套标准化的“听、看、测、调”四步法,精准定位你当前模型训练慢的真实瓶颈点。是数据管道堵了?是显存没喂饱?是通信带宽拉胯?还是代码本身存在隐式同步?只有先回答清楚这些,你才能知道:到底是该租一块H100,还是该重写DataLoader,或是干脆把数据从HDD迁到NVMe SSD。关键词“深度学习”“GPU”“训练速度”不是孤立的标签,它们共同指向一个动态平衡系统——而你的任务,是找到那个最脆弱的支点。
我做深度学习工程支持的十年里,90%以上的“训练慢”问题,根源都不在GPU型号本身。真正决定你每小时能跑多少epoch的,往往是那些藏在train.py文件最底部、被所有人忽略的几行数据加载配置;是nvidia-smi里那个长期低于50%的GPU-Util数值;是你pip list里那个版本老旧、不支持CUDA Graph的torchvision。这篇文章,就是帮你把这些“看不见的墙”一堵堵推倒。它不教你如何吹嘘A100多牛,而是教你怎么用一块RTX 4090,跑出接近A100 80%的实测吞吐量——靠的不是堆硬件,而是对系统底层逻辑的敬畏与掌控。
2. 深度学习训练全流程拆解:GPU只是冰山一角
2.1 训练流水线的四个核心阶段与典型瓶颈分布
深度学习训练绝非“把数据丢给GPU就完事”。它是一个高度协同的流水线作业,可清晰划分为四个连续又相互依赖的阶段:
数据准备(Data Preparation):从磁盘读取原始文件(如JPEG、NPY),解码、解压缩,转换为张量。这是整个流程的起点,也是最容易被低估的瓶颈。想象一下,你的GPU每秒能处理2000张图,但硬盘每秒只能吐出300张——GPU大部分时间都在干等,就像一个顶级赛车手,油门踩到底,却卡在收费站排队。
数据预处理(Data Preprocessing):对已加载的张量进行归一化、随机裁剪、翻转、色彩抖动等增强操作。这部分工作通常在CPU上完成,如果增强逻辑复杂(如自定义几何变换、多尺度采样),会严重拖慢整体节奏。一个典型的反面案例是:用纯Python写的
random_crop函数,在CPU上单线程执行,成了整个pipeline的“减速带”。模型前向/反向传播(Forward/Backward Pass):这才是GPU真正发力的地方。数据送入GPU后,进行矩阵乘、卷积、激活函数等密集计算。但这里有个关键前提:GPU必须被持续、饱满地喂食。如果前面两个阶段供不上,GPU就会“饿着肚子”空转。
参数同步与I/O(Parameter Sync & I/O):在分布式训练中,各GPU计算完梯度后,需通过NCCL等库进行All-Reduce同步;训练过程中,还需将模型权重、日志、检查点(checkpoint)写入磁盘。网络带宽(尤其是多机训练时的RDMA)、磁盘写入速度(特别是频繁保存checkpoint时),都会在此阶段形成新的瓶颈。
提示:一个健康的训练过程,理想状态是GPU Utilization稳定在85%-95%,CPU Utilization(用于数据预处理)在60%-80%,磁盘IO等待时间(
iowait)低于5%。任何一项长期偏离,都意味着该环节存在优化空间。
2.2 GPU型号差异的本质:算力、显存、互联与软件栈
当人们谈论“A100比V100快”时,他们真正比较的,是四个维度的综合表现:
FP16/FP32算力(TFLOPS):这是最直观的指标。A100(SXM4)的FP16算力约312 TFLOPS,而RTX 4090为82 TFLOPS。但这只是理论峰值,实际能达到多少,取决于你的模型是否能充分利用Tensor Core,以及kernel是否经过充分优化。一个没有开启
torch.cuda.amp自动混合精度的ResNet50,跑在A100上,其FP16加速收益几乎为零。显存容量与带宽(Memory Capacity & Bandwidth):A100有40GB/80GB HBM2e显存,带宽高达2TB/s;RTX 4090是24GB GDDR6X,带宽约1TB/s。显存大小决定了你能跑多大的batch size和模型。但带宽才是影响数据搬运速度的关键。当你训练ViT-Large时,显存带宽不足会导致大量时间花在等待数据从显存“搬”到计算单元的路上,此时增加显存容量无济于事,提升带宽才是王道。
GPU间互联(Interconnect):单卡训练时,这个不重要。但一旦进入多卡(尤其是多机)场景,互联方式就是生死线。A100通过NVLink(600GB/s)互联,而消费级显卡只能靠PCIe 4.0(~32GB/s)。这意味着,8卡A100集群的All-Reduce通信效率,可能是8卡4090集群的10倍以上。我曾亲眼见证一个BERT-large的分布式训练,在8卡A100上收敛需要12小时,在8卡4090上,光是梯度同步就占了总时间的40%,最终耗时翻倍。
软件生态与驱动成熟度(Software Stack):这是最容易被忽视的“软实力”。A100作为数据中心级GPU,其CUDA驱动、cuDNN库、NCCL库都经过了数年高强度验证,对各种框架(PyTorch, TensorFlow, JAX)的兼容性和稳定性极佳。而消费级显卡,虽然硬件强大,但在某些特定算子(如
torch.nn.functional.scaled_dot_product_attention的Flash Attention实现)或特定CUDA版本下,可能出现偶发性崩溃,表现为CUDA error: device-side assert triggered或更诡异的d3d device removed(Windows下常见,本质是GPU驱动超时保护机制触发)。
2.3 “租GPU平台”的核心决策树:不是选卡,而是选服务
市面上的GPU云平台,表面看是卖显卡,实质上是卖一套完整的、端到端的计算服务栈。选择平台,本质上是在选择它的“基础设施底座”和“软件交付能力”。以下是几个关键维度的硬核对比:
| 维度 | 典型公有云(AWS EC2 p4d, GCP A2) | 专业AI云(RunPod, Vast.ai) | 本地工作站(自购RTX 4090) |
|---|---|---|---|
| 硬件灵活性 | 固定机型(如p4d.24xlarge=8xA100),升级需重新部署 | 按需租用单卡(A100, H100, 4090),可自由组合 | 完全自主,可随时加装、更换 |
| 存储IO性能 | EBS GP3(~16K IOPS)或专用高性能存储(价格昂贵) | 多数提供SSD直连,但共享存储池性能波动大 | NVMe SSD直连PCIe,IOPS轻松破50万 |
| 网络延迟 | 跨AZ/Region网络延迟高,不适合强通信的分布式训练 | 单机内多卡NVLink/PCIe带宽充足,但跨节点仍是公网 | 无网络瓶颈,所有通信在主板上完成 |
| 软件预装 | 提供标准AMI,需自行配置环境,CUDA版本可能滞后 | 预装主流框架镜像(PyTorch, CUDA),更新快,社区镜像丰富 | 完全自主控制,可定制任意版本组合 |
| 成本模型 | 按小时计费,预留实例可降本,但闲置仍付费 | 竞价模式(Spot)价格极低,但可能被随时回收 | 一次性投入,长期使用成本最低,但前期资金压力大 |
注意:很多新手会陷入“算力陷阱”,只看单卡TFLOPS。但实际项目中,数据IO和网络通信的瓶颈,往往比GPU算力瓶颈出现得更早、更频繁。一个配置了8块A100但只配了普通SATA SSD的云服务器,其训练速度,很可能不如一台配了2块4090+双NVMe SSD的本地工作站。因为前者在数据加载阶段就被卡死了。
3. 实战诊断四步法:手把手定位你的训练瓶颈
3.1 第一步:听——用nvidia-smi和系统监控工具“听”出异常
不要一上来就跑python train.py。先启动一个最简化的、只包含数据加载和模型前向的脚本,然后打开监控终端。
# 在训练脚本运行的同时,新开一个终端 watch -n 1 nvidia-smi # 同时监控CPU和磁盘 htop iostat -x 1你需要重点关注三个数字:
- GPU-Util (%):这是GPU的“心跳”。如果它长期低于60%,说明GPU没吃饱,问题大概率出在前面的数据管道。
- Memory-Usage (MiB):观察显存占用是否稳定。如果它像心电图一样剧烈波动(比如从10GB跳到20GB再跳回),说明你在训练循环里做了不该做的显存分配(如
torch.tensor()未指定device,导致CPU tensor被反复拷贝)。 - Volatile GPU-Util:这个值在多卡训练时尤其重要。如果某张卡的Util远低于其他卡(比如7号卡只有20%,其他都是90%),那基本可以断定是数据分片不均或模型并行策略有问题。
实操心得:我习惯在
train.py开头加一行torch.backends.cudnn.benchmark = True。它会让cuDNN在第一次运行时,自动搜索当前输入尺寸下最快的卷积算法。虽然首次运行会慢一点,但后续所有epoch都会受益。这个小开关,能让ResNet50在A100上的吞吐量提升5%-8%。
3.2 第二步:看——剖析DataLoader,揪出数据加载的“慢先生”
90%的GPU利用率低下,根源都在DataLoader。下面是一段典型的、有问题的代码:
# ❌ 问题代码:默认配置,瓶颈明显 train_loader = DataLoader( dataset=train_dataset, batch_size=64, shuffle=True, num_workers=0, # 关键!单进程,CPU成为瓶颈 pin_memory=False, # 关键!不启用页锁定内存,GPU拷贝慢 )正确的写法,需要三重优化:
num_workers:让CPU“多线程”干活num_workers应设为CPU物理核心数的1.5倍左右(例如16核CPU,设为24)。但要注意:num_workers > 0时,每个worker会fork一个子进程,如果dataset的__getitem__里有全局变量或数据库连接,会引发BrokenPipeError。解决方案是:将所有初始化逻辑(如OpenCV、PIL的初始化)移到__getitem__内部,或使用torch.multiprocessing.set_start_method('spawn')。pin_memory=True:为GPU拷贝铺“高速路”
当pin_memory=True时,DataLoader会将batch数据分配在页锁定(pinned)内存中。GPU可以直接通过DMA(直接内存访问)高速拷贝,速度比普通内存快2-3倍。这是必开选项。persistent_workers=True:避免worker反复启停
默认情况下,每个epoch结束后,所有worker进程会被销毁,下一个epoch再重建。persistent_workers=True会让worker进程在整个训练过程中常驻,省去了反复fork的开销,尤其在epoch数很多时效果显著。
# ✅ 优化后的DataLoader train_loader = DataLoader( dataset=train_dataset, batch_size=64, shuffle=True, num_workers=24, # 根据CPU核心数调整 pin_memory=True, # 必开! persistent_workers=True, # 长epoch必备 prefetch_factor=2, # 预取2个batch,进一步隐藏IO延迟 )常见问题:设置了
num_workers,但nvidia-smi里GPU-Util还是上不去?那很可能是你的__getitem__函数里,用了cv2.imread()这种阻塞式IO操作。解决方案是:改用torchvision.io.read_image()(支持异步),或者将图片提前解码为np.array并缓存到内存(适用于数据集不大时)。
3.3 第三步:测——用torch.utils.benchmark量化每一行代码的耗时
当怀疑某个操作(如自定义的RandomCrop)是瓶颈时,不要猜,要测。PyTorch自带的benchmark模块是神器:
import torch import torchvision.transforms as T from torch.utils.benchmark import Timer # 模拟一个慢的crop操作 def slow_crop(tensor): return tensor[:, 10:200, 10:200] # 简单切片,但假设它很慢 # 模拟一个快的crop操作(使用torchvision内置) fast_crop = T.RandomCrop(size=(190, 190)) # 创建测试张量 x = torch.randn(3, 224, 224, device='cuda') # 测量耗时 timer_slow = Timer(stmt="slow_crop(x)", globals={'slow_crop': slow_crop, 'x': x}) timer_fast = Timer(stmt="fast_crop(x)", globals={'fast_crop': fast_crop, 'x': x}) print(timer_slow.timeit(100)) # 运行100次,取平均 print(timer_fast.timeit(100))这个方法能精确到微秒级,告诉你哪一行代码吃掉了最多时间。我曾用它发现,一个看似简单的torch.cat()操作,在特定shape下,由于内存布局不连续,耗时竟然是torch.stack()的5倍。这种细节,只靠经验无法判断,必须靠数据说话。
3.4 第四步:调——针对性优化:从数据到模型的全链路提速
根据前三步的诊断结果,进行精准打击:
如果瓶颈在数据IO(GPU-Util < 50%, iostat显示%util 100%):
- 将数据集从HDD迁移到NVMe SSD。
- 使用
LMDB或WebDataset格式替代原始文件。LMDB将所有图片打包成一个二进制文件,避免了海量小文件的寻道开销;WebDataset则专为云存储设计,支持流式读取,无需本地下载。 - 开启
torch.compile(model, mode="max-autotune")(PyTorch 2.0+)。它能在运行时对模型的计算图进行极致优化,对CNN类模型,实测可提升15%-30%的吞吐量。
如果瓶颈在CPU预处理(CPU Util 100%, GPU-Util 70%):
- 将
transforms从torchvision.transforms换成albumentations。后者底层用C++和OpenMP编写,对图像增强的加速效果立竿见影。 - 对于文本数据,使用
tokenizers库(Hugging Face出品)替代transformers自带的Tokenizer,其分词速度可提升5倍以上。
- 将
如果瓶颈在GPU计算(GPU-Util > 90%, 但整体速度仍慢):
- 启用混合精度训练:
torch.cuda.amp.autocast()+GradScaler。它能让大部分计算在FP16下进行,显存占用减半,计算速度翻倍,且对模型精度影响极小。 - 使用
torch.compile,并配合mode="reduce-overhead"(减少编译开销)或"max-autotune"(极致性能)。 - 对于Transformer模型,务必开启Flash Attention(需安装
flash-attn包)。它能将self-attention的计算复杂度从O(n²)降到O(n log n),在长序列场景下,速度提升可达3倍。
- 启用混合精度训练:
实操心得:
torch.compile不是银弹。它在首次运行时会有明显的“冷启动”延迟(编译耗时),并且对某些动态shape的模型(如RNN、动态图)支持不佳。我的建议是:在固定输入shape的CNN/ViT项目中,无脑开启max-autotune;在需要动态shape的项目中,先用reduce-overhead模式,再逐步尝试。
4. GPU租用平台深度横评:按需选择,拒绝智商税
4.1 主流平台核心能力矩阵与适用场景
选择租用平台,不是看谁家广告打得响,而是要看它能否完美匹配你项目的技术栈、规模和预算周期。以下是基于我近两年实测的深度横评:
| 平台 | 核心优势 | 典型短板 | 最佳适用场景 | 我的实测单价(USD/hour) |
|---|---|---|---|---|
| Lambda Labs | A100/H100库存充足,网络延迟极低(单机内NVLink),预装环境极其完善(含DeepSpeed, Megatron-LM) | 价格最高,入门门槛高(需申请) | 大模型微调(LLaMA, Qwen)、大规模分布式训练 | A100: $1.20, H100: $3.50 |
| RunPod | 社区镜像丰富(一键部署Stable Diffusion, Llama.cpp),支持Spot竞价(价格仅为On-Demand的1/3),GPU型号选择最多(从3090到H100) | 存储IO不稳定(共享SSD),跨节点网络为公网 | 个人实验、模型推理、中小规模训练(<1B参数) | 4090: $0.45 (Spot), A100: $0.95 (Spot) |
| Vast.ai | 价格最具竞争力(尤其二手卡),支持直接SSH访问裸机,硬件透明度最高 | 新用户审核慢,客服响应滞后,无官方技术支持 | 预算极度紧张的个人开发者、硬件爱好者、定制化需求强的团队 | 3090: $0.18, A100: $0.65 |
| AWS EC2 (p4d/p5) | 企业级SLA保障,与S3无缝集成,安全合规性最强 | 配置僵化(固定机型),存储和网络附加费用高昂,性价比最低 | 金融、医疗等强监管行业,需要审计日志和合规认证的项目 | p4d.24xlarge: $24.48/hour (仅实例) |
提示:“Spot竞价”模式虽便宜,但风险在于实例可能被随时回收。我的应对策略是:在训练脚本中,加入
torch.save定期保存checkpoint,并在程序启动时,自动检测是否存在last_checkpoint.pth,如有则load_state_dict继续训练。这样即使Spot被回收,损失也仅是几分钟的进度。
4.2 避坑指南:那些平台不会告诉你的“隐藏成本”
租GPU,远不止看标价那么简单。以下是我踩过的坑,务必警惕:
存储IO成本黑洞:很多平台宣称“免费赠送100GB SSD”,但这是指系统盘。你的数据集、模型权重、日志,都需要挂载额外的EBS或Cloud Storage。AWS的io2卷,1TB容量+6000 IOPS,每月费用就超过$100。而Lambda Labs的套餐,通常已将高性能存储(NVMe)打包进GPU实例价格里,这才是真正的“全包价”。
网络出口带宽费:当你需要从S3/GCS下载大型数据集(如LAION-5B),或上传训练好的模型到Hugging Face Hub时,会产生巨额的网络出口流量费。AWS的流量费是$0.09/GB,下载1TB数据就是$90。解决方案:优先选择支持对象存储内网直连的平台(如Lambda),或在本地预处理好数据,只上传最小必要集。
驱动与CUDA版本陷阱:某次我在Vast.ai租了一台标称“CUDA 12.1”的A100,结果
nvidia-smi显示驱动是515,而PyTorch 2.1要求驱动>=525。折腾了3小时才搞明白,平台提供的“CUDA版本”是指toolkit版本,而非driver版本。最终只能换平台。教训:租之前,务必在平台文档里确认nvidia-driver --version的输出。
4.3 一份可直接抄作业的租用决策清单
面对琳琅满目的GPU选项,用这份清单快速决策:
你的模型参数量是多少?
- < 100M:RTX 4090 / A10足够,优先选RunPod Spot。
- 100M - 1B:A100 40GB是甜点,Lambda Labs或RunPod On-Demand。
1B:必须H100或A100 80GB,且需多卡NVLink互联,Lambda Labs是唯一可靠选择。
你的数据集有多大?IO模式是什么?
- 小数据集(< 100GB),本地SSD即可:Vast.ai或RunPod。
- 大数据集(> 1TB),且为海量小文件:必须选支持LMDB/WebDataset+NVMe直连的平台(Lambda)。
- 数据在S3/GCS:选与该对象存储有内网直连的平台(AWS, Lambda)。
你的训练周期是长是短?
- 短期实验(< 24小时):RunPod Spot,成本最低。
- 中期项目(1-2周):RunPod或Lambda On-Demand,稳定性优先。
- 长期项目(> 1个月):认真考虑自购工作站。一台双4090+2TB NVMe的工作站,总价约$3500,月均成本远低于云租用。
你的技术栈是否特殊?
- 用DeepSpeed/Megatron:Lambda Labs预装环境最省心。
- 用JAX/Flax:Google Cloud A3(H100)是目前唯一官方支持的云平台。
- 用国产框架(昇思MindSpore):华为云ModelArts是唯一选择。
最后分享一个小技巧:几乎所有平台都提供“免费试用额度”(如Lambda $5, RunPod $10)。不要直接用来跑训练,而是先创建一个最小实例(如1x4090),然后执行
nvidia-smi,df -h,nvidia-smi topo -m,亲自验证硬件规格、存储IO、GPU互联拓扑。这10分钟,能帮你避开90%的“货不对板”陷阱。
5. 常见问题与排查技巧实录:从崩溃到稳定的实战笔记
5.1 “GPU发生崩溃或D3D设备已移除”——Windows下的经典幽灵错误
这个错误在Windows + PyTorch + 多卡训练时高频出现,根本原因不是GPU坏了,而是Windows的TCC(Tesla Compute Cluster)模式与WDDM(Windows Display Driver Model)模式的冲突。WDDM是为图形显示设计的,它会在GPU长时间高负载时,强制进行超时重置(Timeout Detection and Recovery, TDR),以保证桌面响应。而深度学习训练,恰恰就是一种“长时间高负载”。
解决方案:
- 终极方案(推荐):彻底放弃Windows,改用Linux(Ubuntu 22.04 LTS)。Linux内核没有TDR机制,是深度学习的事实标准。
- Windows临时方案:修改注册表,延长TDR timeout。
- 打开
regedit,导航到HKEY_LOCAL_MACHINE\SYSTEM\CurrentControlSet\Control\GraphicsDrivers。 - 新建一个
DWORD (32-bit) Value,命名为TdrDelay。 - 双击它,将数值数据改为
10(单位:秒)。 - 重启电脑。
注意:此操作有风险,可能导致系统无响应。仅作为临时调试手段。
- 打开
5.2 “requires device with capability <= (9, 0) but your gpu has capability (12, 0)”——CUDA架构不兼容
这是PyTorch版本与GPU计算能力(Compute Capability)不匹配的典型报错。(12, 0)是Blackwell架构(如B200, GB200)的代号,而当前(2024年中)的PyTorch稳定版(2.3)尚未正式支持。(9, 0)是Hopper架构(H100)。
根本原因:PyTorch的二进制包是针对特定CUDA Toolkit版本和GPU架构编译的。新GPU发布后,框架厂商需要时间适配。
解决方案:
- 短期:降级到支持你GPU的PyTorch版本。去PyTorch官网的 Previous Versions 页面,查找对应CUDA版本的安装命令。例如,对于H100,应使用
torch==2.1.0+cu118。 - 长期:关注PyTorch nightly build。Nightly版本会第一时间集成对新硬件的支持,虽然稳定性稍差,但对于前沿探索是必需的。安装命令:
pip3 install --pre torch torchvision torchaudio --index-url https://download.pytorch.org/whl/nightly/cu121。
5.3 分布式训练中,GPU利用率不均衡的“七宗罪”
8卡训练,7张卡Util 95%,1张卡Util 30%——这种现象背后,往往藏着代码里的“七宗罪”:
DistributedSampler未正确设置:忘记在DataLoader中传入sampler=DistributedSampler(dataset),导致所有卡都读取了全部数据。torch.nn.parallel.DistributedDataParallel(DDP)封装位置错误:必须在model.to(device)之后,optimizer初始化之前进行封装。顺序错了,DDP就形同虚设。torch.cuda.empty_cache()滥用:在训练循环里频繁调用,会强制同步,打断GPU流水线。torch.no_grad()范围过大:在验证阶段,no_grad应只包裹forward,而不应包裹整个val_step,否则loss.item()会因梯度图未释放而变慢。torch.distributed.barrier()误用:在不需要同步的地方(如每个epoch结束后的日志打印)加了barrier,导致快卡要等慢卡。torch.cuda.Stream未正确管理:自定义CUDA kernel时,未将stream绑定到正确的GPU上下文。torch.set_num_threads(1)缺失:在多进程DataLoader中,每个worker的PyTorch线程数未限制,导致CPU资源争抢。
排查技巧:在DDP训练中,给每张卡的日志加上
rank标识。例如:print(f"[Rank {args.rank}] Epoch {epoch} finished")。通过观察不同rank的日志时间戳,就能一眼看出哪张卡是“拖油瓶”。
5.4 一份精简的“训练稳定性Checklist”
这是我放在每个新项目README.md里的清单,确保上线前万无一失:
- [ ]
nvidia-smi确认GPU驱动版本 >= PyTorch要求的最低版本。 - [ ]
torch.cuda.is_available()返回True,且torch.cuda.device_count()等于预期卡数。 - [ ]
DataLoader已启用pin_memory=True和persistent_workers=True。 - [ ]
torch.backends.cudnn.benchmark = True已设置。 - [ ] 混合精度训练(
autocast+GradScaler)已开启。 - [ ]
torch.compile已在支持的模型上启用。 - [ ]
DistributedSampler已正确注入DataLoader(分布式训练)。 - [ ] 所有
tensor操作均已指定device,无隐式CPU-GPU拷贝。 - [ ]
checkpoint保存路径已确认有足够磁盘空间,且路径为绝对路径。 - [ ]
wandb/tensorboard等监控工具的初始化,已放在if rank == 0条件下(分布式训练)。
这份清单,是我过去十年,从无数个凌晨三点的崩溃现场里,一点点攒出来的。它不能保证你永不犯错,但能让你的第一次训练,就站在一个坚实的基础上。毕竟,深度学习的浪漫,不在于堆砌最贵的硬件,而在于用最朴素的工具,解开最复杂的方程。当你终于看到GPU-Util稳稳地停在92%,而loss曲线坚定地下滑时,那种掌控感,远胜于任何显卡的跑分。