大规模训练的一些奇技淫巧
1. 分布式训练
1.1 数据并行
数据并行是指,通过将将模型(整个)在不同的设备部署多个副本,每个设备可以处理不同的batch,那么整体而言,我们就增大了训练时数据的吞吐量。从而加速了训练:
1.2 模型并行
对不起,我没用过这么大的模型。。。但是,基本思路就是你在一个device算完模型的一部分之后,在to到另一个device就行了,参考下面:
2. torch里的一些奇技淫巧
在torch里进行dataParallel, 我们大概来说有两个接口可以用使用:
- torch.nn.DataParallel 好多人叫做DP模式
- 前向过程的时候,DataParallel 会将输入数据平均分配成多个子部分,然后送入不同的device里;同时,DataParallel会将模型在每个device里拷贝一份。然后在反向传播的时候,不同模型副本的梯度会叠加到原始的模型上去。(这里稍微有个小坑,output_divice这个参数默认是0,然后参考是os.environ[“CUDA_VISIBLE_DEVICES”] ,所以如果你没指定,但是用的又不是gpu0的化,麻烦设置下os.environ[“CUDA_VISIBLE_DEVICES”] )
device_ids = [0, 1]
net = torch.nn.DataParallel(net, device_ids=device_ids,output_divice)
# 优化器
optimizer = torch.optim.SGD(net.parameters(), lr=lr)
optimizer = nn.DataParallel(optimizer, device_ids=device_ids)
这个接口会自动对数据分配到多个GPU里去,如下面的 [0, 1]两个GPU面,但是这个接口有一个比较坑的地方,就是,注意这个参数output_divice, 他虽然在input的时候是两块/多块卡一起在跑,然后所有其他卡的loss的计算的时候都要加到这个output_divice指定卡上去(如果指定就是device_ids[0]),这很可能导致极度的负载不均衡。
- torch.nn.parallel.DistributedDataParallel 好多人叫做DDP模式
- 首先,相对于DP,无脑推荐DDP。好处是:
- DDP的每个进程是一个独立的训练过程,它只对梯度等少量数据进行信息交换(DP只有一个进程,控制多个GPU);然后DDP的梯度在各个进程独立计算,然后汇总到rank=0的进程(设备),并将其broadcast到各个进程里,注意,这里初始化相同,平均后更新的梯度相同,所以,模型一只相同。而dp是在主的那个gpu上更新好新的模型参数,然后复制模型到其他的设备上去,这会有更大数据传输
- 每个进程包含独立的解释器和 GIL。cpython,解除一些严重依赖python运行时的模块,比如rnn。
- 首先,相对于DP,无脑推荐DDP。好处是: