Python Gluon参数和模块命名操作教程
Python  /  管理员 发布于 7年前   244
本文实例讲述了Python Gluon参数和模块命名操作。分享给大家供大家参考,具体如下:
在gluon里,每个参数和块都有一个名字(和前缀)。参数名可以由用户指定,block名也可以由用户指定,也可以自动创建。
本教程中,我们将讨论命名方面的最佳实践。首先,import MXNet和Gluon
from __future__ import print_functionimport mxnet as mxfrom mxnet import gluon
在创建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_params
和save
/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。
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
features
,输出层叫 output
.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程序设计有所帮助。
122 在
学历:一种延缓就业设计,生活需求下的权衡之选中评论 工作几年后,报名考研了,到现在还没认真学习备考,迷茫中。作为一名北漂互联网打工人..123 在
Clash for Windows作者删库跑路了,github已404中评论 按理说只要你在国内,所有的流量进出都在监控范围内,不管你怎么隐藏也没用,想搞你分..原梓番博客 在
在Laravel框架中使用模型Model分表最简单的方法中评论 好久好久都没看友情链接申请了,今天刚看,已经添加。..博主 在
佛跳墙vpn软件不会用?上不了网?佛跳墙vpn常见问题以及解决办法中评论 @1111老铁这个不行了,可以看看近期评论的其他文章..1111 在
佛跳墙vpn软件不会用?上不了网?佛跳墙vpn常见问题以及解决办法中评论 网站不能打开,博主百忙中能否发个APP下载链接,佛跳墙或极光..
Copyright·© 2019 侯体宗版权所有·
粤ICP备20027696号