Torch-RNN运行过程中的坑 [1](读取Lua非空table,size为0)
内容导读
互联网集市收集整理的这篇技术教程文章主要介绍了Torch-RNN运行过程中的坑 [1](读取Lua非空table,size为0),小编现在分享给大家,供广大互联网技能从业者学习和参考。文章包含3125字,纯文字阅读大概需要5分钟。
内容图文
![Torch-RNN运行过程中的坑 [1](读取Lua非空table,size为0)](/upload/InfoBanner/zyjiaocheng/1175/30327e263ae2410e969118f53ec475dc.jpg)
0、踩坑背景
执行Torch-RNN的时候,在LanguageModel.lua中的encode_string函数中,对start_text的各个character进行id映射编码,实现功能类似“北京天安门”-->“5 10 88 32 111”,方便后面的计算。
这个函数会利用一个全局的类似HashMap的table,hashmap中的key是character(char),value是id(int),涉及到一个从hashmap中按照key取值的操作,代码如下:
local idx = self.token_to_idx[token] assert(idx ~= nil, ‘Got invalid idx‘)
但是每次运行到assert语句时,都会报错,返回的是nil。
我的训练数据集的规模足够大,同时编码正确的情况下,那么我就需要从几个方面debug:
- 这个字典table文件压根没数据(本文测试的内容)
- token确实在table中未命中
我对 self.token_to_idx 这个table类型的变量的大小,进行打印的时候,采用了多种方式:
print (table.getn(self.token_to_idx)) print(table.maxn(self.token_to_idx)) print(#self.token_to_idx)
但是输出都为0,奇了怪了,我用如下语句打印这个table,是有值的:
for k,v inpairs(self.token_to_idx) doprint(k,v) end
--------------------------------------------------------------------
那么这是为什么呢?明明table不为空,取table size的时候都是0?
1、lua中的table是什么,各种size函数的区别?
在上一篇《Torch-RNN运行过程中的坑 [0](一些基础概念)》中,我们了解到了lua的introduction中有一句:
自动内存管理;只提供了一种通用类型的表(table),用它可以实现数组,哈希表,集合,对象;
也就是说lua中的数组和hashmap两种数据类型是合并的,美其名曰通用类型的表。
table的API本篇不研究,抛一个链接:Lua table(表),我们先研究一下咱们碰到的问题,即如何取table的真实size。
下面有四种方法(均在Lua 5.14下进行):
- table.getn(t)
返回table中元素的个数。给出一个调用例子:
> t1 = {1, 2, 3, 5}; > print(table.getn(t1)) 4 > t2 = {[1]=1,[2]=2,[3]=3,[4]=5}; > print(table.getn(t2)) 4
这不正和我们的要求吻合嘛,继续试试:
> t3 = {[1]=1,[2]=2,[3]=3,[6]=5}; > print(table.getn(t2)) 3--第4个元素下标为6,非连续 > t4 = {[1]=1,[2]=2,nil,[6]=5}; > print(table.getn(t4)) 0--有nil,长度异常 > t5 = {[1]=1,["2"]=2,nil,[6]=5}; > print(table.getn(t5)) 0--有nil,长度异常 > t6 = {[1]=1,["2"]=2,[6]=5}; > print(table.getn(t6)) 1--1后面没有2,没连续上 > t7 = {[1]=1,["2"]=2,[2]=5}; > print(table.getn(t7)) 2--即使1和2两个index没有写连上,但是table首先排序后,计数为2 > t8 = {["20"]=1,["2"]=2,["3"]=5}; > print(table.getn(t8)) 0--hashmap型长度异常
好像出问题了,在index不连续的情况下、在含有nil的情况下、有hashmap、数组与hashmap混搭等情况下getn返回的结果都不正常。
----------------------------------------------------------------------------------------------------------
lua的table长度问题中,作者提出了table可以存储两种类型,一种是list类型(数组,key必为正整数),另外一种是record类型(hashmap,key为非正整数),getn函数统计的是连续的key为正整数的数目,所以我们看头两个例子是输出正常的。
所以没必要记这个规律,除了上面几个例子,getn肯定还有一些其他的规律没发现,不过记住这个getn函数要在有序正整数key的size计数时,输出才是正确的。。。
- table.maxn(t)
Lua中的table函数库中总结的很好,在这里引用一下:
table.maxn()函数返回指定table中所有正数key值中最大的key值. 如果不存在key值为正数的元素, 则返回0. 此函数不限于table的数组部分.
下面的例子也搬运一下:
> tbl = {[1] = "a", [2] = "b", [3] = "c", [26] = "z"} > print(#tbl) 3-- 因为26和之前的数字不连续, 所以不算在数组部分内 > print(table.maxn(tbl)) 26
> tbl[91.32] = true > print(table.maxn(tbl)) 91.32
- #t
#方法取size,经测试,效果上应该与getn()方法一毛一样。从1开始,连续整数key的元素个数(必须从1开始计数,结果才正常)。再抛几个例子,希望看官不要花眼。。。
> t5 = {[1]=1,[9]=2,["22"]=9,[2]=5}; > print(#t5) 2--1和2连续 > t5 = {[1]=1,[9]=2,["22"]=9,[0]=5}; > print(#t5) 1--从1开始计数,下一个就是9了,不连续 > t5 = {[2]=1,[9]=2,["22"]=9,[5]=5}; > print(#t5) 0--没从1开始计数,非常遗憾
- for遍历cnt++
那么难道没有API可以对hashmap计数了吗?让我这个Java流选手写Lua情何以堪。。。最后找了一位同学同样的疑问,它使用了for循环对key-value计数。。。
function count(ht) local n = 0; for _, v inpairs(ht) do n = n + 1; endreturn n; end
2、重点来啦,那么解决问题的方法?
相信大家看完文章,答案自然成竹于胸,也是很尴尬。那就是:
Lua中“hashmap型”table的元素计数,还得用for循环cnt++的方法。。。。
3、结论与感慨
该踩的坑还是得踩啊。。。
原文:http://www.cnblogs.com/zklidd/p/6106600.html
内容总结
以上是互联网集市为您收集整理的Torch-RNN运行过程中的坑 [1](读取Lua非空table,size为0)全部内容,希望文章能够帮你解决Torch-RNN运行过程中的坑 [1](读取Lua非空table,size为0)所遇到的程序开发问题。 如果觉得互联网集市技术教程内容还不错,欢迎将互联网集市网站推荐给程序员好友。
内容备注
版权声明:本文内容由互联网用户自发贡献,该文观点与技术仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 gblab@vip.qq.com 举报,一经查实,本站将立刻删除。
内容手机端
扫描二维码推送至手机访问。