1.修改CPU版本的pytorch模型到GPU版本


从github上git下来的CNNs程序需要将分类结果在opencv上显示,图片是采用单帧处理,因此每一帧的图片返回类别与置信度的速度需要加快,于是想到该CPU版本的模型到GPU版本。

在参考网上的文档和博客后,发现只要在模型和参数后加.cuda()即可将模型由cpu上的运算调到gpu上运算。

首先需要确定自己的pytorch版本能否进行gpu计算。
print (torch.cuda.is_available())
如果结果是True,则可以进行gpu计算,如果是False,就需要安装gpu版本的torch或是CUDA了。还可以通过
print (torch.cuda.device_count())
来识别可以使用的gpu个数。

话不多说,找到git下来代码中的模型和参数,然后加.cuda:
原始代码如下:
model = models.__dict__[arch](num_classes=365)#模型 checkpoint =
torch.load(model_file, map_location=lambda storage, loc: storage)#模型 ... img =
Image.open(img_name) input_img = V(centre_crop(img).unsqueeze(0))#参数 # forward
pass logit = model.forward(input_img) h_x = F.softmax(logit, 1).data.squeeze()
probs, idx = h_x.sort(0, True)
得到的分类结果:
resnet18 prediction on 0003.jpeg 0.297 -> field_road 0.196 -> golf_course 0.101
-> pasture0.077 -> soccer_field 0.070 -> wheat_field elapse time is
0.11690378189086914
预测类别的时间约为0.11s
加上.cuda()的程序后
model = models.__dict__[arch](num_classes=365).cuda() checkpoint =
torch.load(model_file, map_location=lambda storage, loc: storage.cuda()) ...
img = Image.open(img_name) input_img = V(centre_crop(img).unsqueeze(0)).cuda()
...# forward pass logit = model.forward(input_img) h_x = F.softmax(logit, 1
).data.squeeze() probs, idx = h_x.sort(0, True)
得到的分类结果:
resnet18 prediction on 0003.jpeg 0.297 -> field_road 0.196 -> golf_course 0.101
-> pasture0.077 -> soccer_field 0.070 -> wheat_field elapse time is
0.03774833679199219
前向计算时间为0.037748s

计算速度约提升3倍,GPU加速效果明显。

参考资料:
1.pytorch通过torch.cuda使用GPU加速运算且比较GPU与CPU运算效果以及应用场景
<https://ptorch.com/news/53.html>
2.浅谈将Pytorch模型从CPU转换成GPU
<https://blog.csdn.net/qq_28444159/article/details/78781201>
3.pytorch在CPU和GPU上加载模型 <https://blog.csdn.net/dcrmg/article/details/79503978>

2.TypeError:CUDA tensor to numpy

将另一段代码中的weight_softmax = params[-2]data.numpy()改成weight_softmax =
params[-2].cuda().data.numpy()时会报错:
TypeError: can't convert CUDA tensor to numpy. Use Tensor.cpu() to copy the
tensor to host memory first.
参考stackflow
<https://stackoverflow.com/questions/44340848/how-to-convert-pytorch-autograd-variable-to-numpy>
上面的回答,如果想把CUDA tensor格式的数据改成numpy时,需要先将其转换成cpu float-tensor随后再转到numpy格式。
即,修改
x.data.numpy()

x.data.cpu().numpy()
即可

因此再修改weight_softmax = params[-2].cuda().data.numpy()
为weight_softmax = params[-2].cuda().data.cpu().numpy()运行正常。