加入收藏 | 设为首页 | 会员中心 | 我要投稿 甘孜站长网 (https://www.0836zz.com.cn/)- 运维、物联设备、数据计算、智能推荐、云管理!
当前位置: 首页 > 运营中心 > 建站资源 > 经验 > 正文

PyTorch最佳实践,怎样才能写出一手风格优美的代码

发布时间:2019-05-07 14:21:49 所属栏目:经验 来源:机器之心编译
导读:虽然这是一个非官方的 PyTorch 指南,但本文总结了一年多使用 PyTorch 框架的经验,尤其是用它开发深度学习相关工作的最优解决方案。请注意,我们分享的经验大多是从研究和实践角度出发的。 这是一个开发的项目,欢迎其它读者改进该文档: https://github.
副标题[/!--empirenews.page--]

虽然这是一个非官方的 PyTorch 指南,但本文总结了一年多使用 PyTorch 框架的经验,尤其是用它开发深度学习相关工作的最优解决方案。请注意,我们分享的经验大多是从研究和实践角度出发的。

这是一个开发的项目,欢迎其它读者改进该文档:

https://github.com/IgorSusmelj/pytorch-styleguide。

本文档主要由三个部分构成:首先,本文会简要清点 Python 中的最好装备。接着,本文会介绍一些使用 PyTorch 的技巧和建议。最后,我们分享了一些使用其它框架的见解和经验,这些框架通常帮助我们改进工作流。

一、清点 Python 装备

1. 建议使用 Python 3.6 以上版本

根据我们的经验,我们推荐使用 Python 3.6 以上的版本,因为它们具有以下特性,这些特性可以使我们很容易写出简洁的代码:

  • 自 Python 3.6 以后支持「typing」模块
  • 自 Python 3.6 以后支持格式化字符串(f string)

2. Python 风格指南

我们试图遵循 Google 的 Python 编程风格。请参阅 Google 提供的优秀的 python 编码风格指南:

地址:https://github.com/google/styleguide/blob/gh-pages/pyguide.md。

在这里,我们会给出一个最常用命名规范小结:

PyTorch最佳实践,怎样才能写出一手风格优美的代码

3. 集成开发环境

一般来说,我们建议使用 visual studio 或 PyCharm 这样的集成开发环境。而 VS Code 在相对轻量级的编辑器中提供语法高亮和自动补全功能,PyCharm 则拥有许多用于处理远程集群任务的高级特性。

4. Jupyter Notebooks VS Python 脚本

一般来说,我们建议使用 Jupyter Notebook 进行初步的探索,或尝试新的模型和代码。如果你想在更大的数据集上训练该模型,就应该使用 Python 脚本,因为在更大的数据集上,复现性更加重要。

我们推荐你采取下面的工作流程:

  • 在开始的阶段,使用 Jupyter Notebook
  • 对数据和模型进行探索
  • 在 notebook 的单元中构建你的类/方法
  • 将代码移植到 Python 脚本中
  • 在服务器上训练/部署

5. 开发常备库

常用的程序库有:

6. 文件组织

不要将所有的层和模型放在同一个文件中。最好的做法是将最终的网络分离到独立的文件(networks.py)中,并将层、损失函数以及各种操作保存在各自的文件中(layers.py,losses.py,ops.py)。最终得到的模型(由一个或多个网络组成)应该用该模型的名称命名(例如,yolov3.py,DCGAN.py),且引用各个模块。

主程序、单独的训练和测试脚本应该只需要导入带有模型名字的 Python 文件。

二、PyTorch 开发风格与技巧

我们建议将网络分解为更小的可复用的片段。一个 nn.Module 网络包含各种操作或其它构建模块。损失函数也是包含在 nn.Module 内,因此它们可以被直接整合到网络中。

继承 nn.Module 的类必须拥有一个「forward」方法,它实现了各个层或操作的前向传导。

一个 nn.module 可以通过「self.net(input)」处理输入数据。在这里直接使用了对象的「call()」方法将输入数据传递给模块。

  1. output = self.net(input) 

1. PyTorch 环境下的一个简单网络

使用下面的模式可以实现具有单个输入和输出的简单网络:

  1. class ConvBlock(nn.Module): 
  2.     def __init__(self): 
  3.         super(ConvBlock, self).__init__() 
  4.         block = [nn.Conv2d(...)] 
  5.         block += [nn.ReLU()] 
  6.         block += [nn.BatchNorm2d(...)] 
  7.         self.block = nn.Sequential(*block) 
  8.  
  9.     def forward(self, x): 
  10.         return self.block(x) 
  11.  
  12. class SimpleNetwork(nn.Module): 
  13.     def __init__(self, num_resnet_blocks=6): 
  14.         super(SimpleNetwork, self).__init__() 
  15.         # here we add the individual layers 
  16.         layers = [ConvBlock(...)] 
  17.         for i in range(num_resnet_blocks): 
  18.             layers += [ResBlock(...)] 
  19.         self.net = nn.Sequential(*layers) 
  20.  
  21.     def forward(self, x): 
  22.         return self.net(x) 

(编辑:甘孜站长网)

【声明】本站内容均来自网络,其相关言论仅代表作者个人观点,不代表本站立场。若无意侵犯到您的权利,请及时与联系站长删除相关内容!

热点阅读