Python Gluon参数和模块命名操作教程


Posted in Python onDecember 18, 2019

本文实例讲述了Python Gluon参数和模块命名操作。分享给大家供大家参考,具体如下:

Gluon参数和模块命名教程

在gluon里,每个参数和块都有一个名字(和前缀)。参数名可以由用户指定,block名也可以由用户指定,也可以自动创建。

本教程中,我们将讨论命名方面的最佳实践。首先,import MXNet和Gluon

from __future__ import print_function
import mxnet as mx
from mxnet import gluon

Blocks命名

在创建block时,可以指定一个前缀给它:

mydense = gluon.nn.Dense(100, prefix='mydense_')
print(mydense.prefix)
mydense_

若没有指定前缀,gluon会自动生成一个前缀

dense0 = gluon.nn.Dense(100)
print(dense0.prefix)
dense0_

当你创建更多同类块时,它们将递增后缀命名,以避免冲突:

dense1 = gluon.nn.Dense(100)
print(dense1.prefix)
dense1_

参数命名

blocks中的参数将用过将block的前缀添加到参数的名称来命名:

print(dense0.collect_params())
dense0_ (
 Parameter dense0_weight (shape=(100, 0), dtype=<type 'numpy.float32'>)
 Parameter dense0_bias (shape=(100,), dtype=<type 'numpy.float32'>)
)

名称空间

为了管理嵌套block的名称,每个块附加有一个name_scope(名称空间)。在name_scope中创建的block都会在其名称前加上父block的名称。

我们将定义一个简单的神经网络来说明这点:

class Model(gluon.Block):
 def __init__(self, **kwargs):
  super(Model, self).__init__(**kwargs)
  with self.name_scope():
   self.dense0 = gluon.nn.Dense(20)
   self.dense1 = gluon.nn.Dense(20)
   self.mydense = gluon.nn.Dense(20, prefix='mydense_')
 def forward(self, x):
  x = mx.nd.relu(self.dense0(x))
  x = mx.nd.relu(self.dense1(x))
  return mx.nd.relu(self.mydense(x))

现在实例化这个神经网络

  • 注意:model0.dense0的名称是model0_dense0_而非dense0_
  • 注意:我们指定model.mydense的前缀为mydense_,它的父类前缀会自动生成并添加到前面变成model0_mydense_

这里的名称前缀和变量名model0没有关系,这里就算把model0换成其他变量名比如net,前缀还是model?,? 表示这是一个递增的数字,这里的名称前缀和class Model有关 若将类名Model换成Hodel,那么后面的前缀都会变成 hodel?

model0 = Model()
model0.initialize()
model0(mx.nd.zeros((1, 20)))
print(model0.prefix)
print(model0.dense0.prefix)
print(model0.dense1.prefix)
print(model0.mydense.prefix)
model0_
model0_dense0_
model0_dense1_
model0_mydense_

若我们再次实例化Model,在Dense前会生成一个不同的名称。

  • 注意:model1.dense0的名称依然是dense0_而非dense2_,遵循之前在model0中创建的dense层的命名规则。这是因为每个model的命名空间是相互独立
model1 = Model()
print(model1.prefix)
print(model1.dense0.prefix)
print(model1.dense1.prefix)
print(model1.mydense.prefix)
model1_
model1_dense0_
model1_dense1_
model1_mydense_

建议手动为顶层的model指定一个前缀,即model = Model(prefix=‘mymodel_'),以避免命名时可能出现的混淆。

相同的规则同样适用于像Sequential这类容器block.name_scope 既可以在__init__内使用,也可以在__init__ 外使用:

注意:这里Sequential也有参数prefix,是可以自己指定名称的,不指定的话就叫Sequential

net = gluon.nn.Sequential()
with net.name_scope():
 net.add(gluon.nn.Dense(20))
 net.add(gluon.nn.Dense(20))
print(net.prefix)
print(net[0].prefix)
print(net[1].prefix)
sequential0_
sequential0_dense0_
sequential0_dense1_

gluon.model_zoo也一样

net = gluon.nn.Sequential()
with net.name_scope():
 net.add(gluon.model_zoo.vision.alexnet(pretrained=True))
 net.add(gluon.model_zoo.vision.alexnet(pretrained=True))
print(net.prefix, net[0].prefix, net[1].prefix)
sequential1_ sequential1_alexnet0_ sequential1_alexnet1_

保存和载入

由于model0和model1有不同的前缀,所以它们的参数是有不同名字的:

print(model0.collect_params(), '\n')
print(model1.collect_params())
model0_ (
 Parameter model0_dense0_weight (shape=(20L, 20L), dtype=<type 'numpy.float32'>)
 Parameter model0_dense0_bias (shape=(20L,), dtype=<type 'numpy.float32'>)
 Parameter model0_dense1_weight (shape=(20L, 20L), dtype=<type 'numpy.float32'>)
 Parameter model0_dense1_bias (shape=(20L,), dtype=<type 'numpy.float32'>)
 Parameter model0_mydense_weight (shape=(20L, 20L), dtype=<type 'numpy.float32'>)
 Parameter model0_mydense_bias (shape=(20L,), dtype=<type 'numpy.float32'>)
) 
model1_ (
 Parameter model1_dense0_weight (shape=(20, 0), dtype=<type 'numpy.float32'>)
 Parameter model1_dense0_bias (shape=(20,), dtype=<type 'numpy.float32'>)
 Parameter model1_dense1_weight (shape=(20, 0), dtype=<type 'numpy.float32'>)
 Parameter model1_dense1_bias (shape=(20,), dtype=<type 'numpy.float32'>)
 Parameter model1_mydense_weight (shape=(20, 0), dtype=<type 'numpy.float32'>)
 Parameter model1_mydense_bias (shape=(20,), dtype=<type 'numpy.float32'>)
)

若你尝试将model0的参数载入到model1中,你将会得到一个名称不匹配的错误

model0.collect_params().save('model.params')
try:
 model1.collect_params().load('model.params', mx.cpu())
except Exception as e:
 print(e)

Parameter 'model1_dense0_weight' is missing in file 'model.params', which contains parameters: 'model0_mydense_weight', 'model0_dense1_bias', 'model0_dense1_weight', 'model0_dense0_weight', 'model0_dense0_bias', 'model0_mydense_bias'. Please make sure source and target networks have the same prefix.

为了解决这个问题,我们使用save_parameters/load_parameters而不是 collect_paramssave/load. save_parameters。使用模型结构而非参数名称来匹配参数。

model0.save_parameters('model.params')
model1.load_parameters('model.params')
print(mx.nd.load('model.params').keys())
['dense0.bias', 'mydense.bias', 'dense1.bias', 'dense1.weight', 'dense0.weight', 'mydense.weight']

替换网络中的block并进行fine-turning

有时需要加载一些预训练的模型,并替换其中某些block并进行fine-turning。

For example, the alexnet in model zoo has 1000 output dimensions, but maybe you only have 100 classes in your application.

例如,alexnet有1000个输出维度但你只有100类。

我们首先载入预训练的AlexNet

  • 在Gluon Model Zoo,所有图像分类模型的格式都是特征提取层叫 features ,输出层叫 output.
  • 注意到输出层是一个dense block,有1000个维度的输出
alexnet = gluon.model_zoo.vision.alexnet(pretrained=True)
print(alexnet.output)
print(alexnet.output.prefix)
Dense(4096 -> 1000, linear)
alexnet0_dense2_

改变输出为100维,使用一个新block替换它

with alexnet.name_scope():
 alexnet.output = gluon.nn.Dense(100)
alexnet.output.initialize()
print(alexnet.output)
print(alexnet.output.prefix)
Dense(None -> 100, linear)
alexnet0_dense3_

原文:http://mxnet.incubator.apache.org/versions/master/tutorials/gluon/naming.html

更多关于Python相关内容可查看本站专题:《Python数学运算技巧总结》、《Python图片操作技巧总结》、《Python数据结构与算法教程》、《Python函数使用技巧总结》、《Python字符串操作技巧汇总》及《Python入门与进阶经典教程》

希望本文所述对大家Python程序设计有所帮助。

Python 相关文章推荐
Python中使用装饰器和元编程实现结构体类实例
Jan 28 Python
Python 序列的方法总结
Oct 18 Python
在python3.5中使用OpenCV的实例讲解
Apr 02 Python
python opencv实现图像边缘检测
Apr 29 Python
使用python爬取抖音视频列表信息
Jul 15 Python
python 的 scapy库,实现网卡收发包的例子
Jul 23 Python
Python closure闭包解释及其注意点详解
Aug 28 Python
Django 请求Request的具体使用方法
Nov 11 Python
解决python-docx打包之后找不到default.docx的问题
Feb 13 Python
利用Tensorboard绘制网络识别准确率和loss曲线实例
Feb 15 Python
python画环形图的方法
Mar 25 Python
Python图像处理库PIL详细使用说明
Apr 06 Python
python turtle 绘制太极图的实例
Dec 18 #Python
Python使用gluon/mxnet模块实现的mnist手写数字识别功能完整示例
Dec 18 #Python
简单了解Python读取大文件代码实例
Dec 18 #Python
python 比较2张图片的相似度的方法示例
Dec 18 #Python
使用Python的Turtle库绘制森林的实例
Dec 18 #Python
python3 requests库实现多图片爬取教程
Dec 18 #Python
在notepad++中实现直接运行python代码
Dec 18 #Python
You might like
DC这些乐高系列动画电影你看过几部?
2020/04/09 欧美动漫
笑谈配置,使用Smarty技术
2007/01/04 PHP
PHP中new static()与new self()的比较
2016/08/19 PHP
php文件上传 你真的掌握了吗
2016/11/28 PHP
PHP十六进制颜色随机生成器功能示例
2017/07/24 PHP
利用PHP获取汉字首字母并且分组排序详解
2017/10/22 PHP
PHP autoload使用方法及步骤详解
2020/09/05 PHP
javascript attachEvent和addEventListener使用方法
2009/03/19 Javascript
Jquery从头学起第四讲 jquery入门教程
2010/08/01 Javascript
jQuery让控件左右移动的三种实现方法
2013/09/08 Javascript
几种设置表单元素中文本输入框不可编辑的方法总结
2013/11/25 Javascript
防止按钮在短时间内被多次点击的方法
2014/03/10 Javascript
常见浏览器多长时间会提示“脚本运行时间过长”总结
2014/04/29 Javascript
JavaScript人脸识别技术及脸部识别JavaScript类库Tracking.js
2015/09/14 Javascript
Underscore之Array_动力节点Java学院整理
2017/07/10 Javascript
jQuery实现的粘性滚动导航栏效果实例【附源码下载】
2017/10/19 jQuery
React+Antd+Redux实现待办事件的方法
2019/03/14 Javascript
vue的keep-alive中使用EventBus的方法
2019/04/23 Javascript
微信小程序获取用户信息及手机号(后端TP5.0)
2019/09/12 Javascript
基于JS+HTML实现弹窗提示是否确认提交功能
2020/06/17 Javascript
vue+element实现动态加载表单
2020/12/13 Vue.js
基于Django的ModelForm组件(详解)
2017/12/07 Python
numpy排序与集合运算用法示例
2017/12/15 Python
python3.5+tesseract+adb实现西瓜视频或头脑王者辅助答题
2018/01/17 Python
Python中一般处理中文的几种方法
2019/03/06 Python
浅谈Python2之汉字编码为unicode的问题(即类似\xc3\xa4)
2019/08/12 Python
python 制作网站小说下载器
2021/02/20 Python
HTML5实现移动端复制功能
2018/04/19 HTML / CSS
FLOS美国官网:意大利高级照明工艺的传奇
2018/08/07 全球购物
英国领先的在线高尔夫设备零售商:Golfgeardirect
2020/12/11 全球购物
eDreams德国:南欧领先的在线旅游公司
2020/12/07 全球购物
什么情况下你必须要把一个类定义为abstract的
2013/01/06 面试题
物流经理自我评价
2013/09/23 职场文书
倡议书范文大全
2015/04/28 职场文书
2015年小学重阳节活动总结
2015/07/29 职场文书
HTML+css盒子模型案例(圆,半圆等)“border-radius” 简单易上手
2021/05/10 HTML / CSS