Lua泛型for遍历table时ipairs与pairs的区别

喵·引言

当欲使用泛型for遍历Lua表时,有两种方式,即

for i,v in ipairs(tableName) do
    print(i,v);
end
for k,v in pairs(tableName) do
    print(k,v);
end

二者只有一处不同,即ipairs与pairs,那么二者有何区别呢?

动手尝梨子

定义三个表,根据它们内容的不同,分别把它们叫做“纯数组”,“纯表”,“杂表1”,“杂表2”。请注意:这种称呼是非常不严谨的,因为它们都是table,即表。


-- '纯数组'
testTab ={1,2,3,4,5};
-- '纯表'
testTab1 = {a = 1, b = 2, c =3};
-- '杂表1'
testTab2 = {"zi",a = 5,b = 10, c = 15,"miao","chumo"};
-- '杂表2'
testTab3 = {"zi",a = 5,b = 10, c = 15,"miao",nil,"chumo"};

ipairs与pairs遍历纯数组

代码如下所示:

for i,v in ipairs(tableName) do
print("ipairs遍历纯数组");
for i,v in ipairs(testTab) do
    print(i,v);
end
    print("pairs遍历纯数组");
for k,v in pairs(testTab) do
    print(k,v);
end

输出结果为:

for i,v in ipairs(tableName) do
ipairs遍历纯数组
1 1
2 2
3 3
4 4
5 5
pairs遍历纯数组
1 1
2 2
3 3
4 4
5 5

首次运行,二者结果无任何区别,多次运行,二者结果无任何区别。

ipairs与pairs遍历纯表

代码如下所示:

for i,v in ipairs(tableName) do
print("ipairs遍历纯表");
for i,v in ipairs(testTab1) do
    print(i,v);
end
print("pairs遍历纯表");
for k,v in pairs(testTab1) do
    print(k,v);
end

输出结果为:

for i,v in ipairs(tableName) do
ipairs遍历纯表
pairs遍历纯表
c 3
a 1
b 2

首次运行,ipairs一组无输出,pairs有输出。
多次运行,ipairs一组无输出,pairs一组输出顺序改变,即a,b,c输出顺序改变。

ipairs与pairs遍历杂表1

代码如下所示:

for i,v in ipairs(tableName) do
print("ipairs遍历杂表1");
for i,v in ipairs(testTab2) do
print(i,v);
end
print("pairs遍历杂表1");
for k,v in pairs(testTab2) do
print(k,v);
end

输出结果为:

for i,v in ipairs(tableName) do
ipairs遍历杂表1
1 zi
2 miao
3 chumo
pairs遍历杂表1
1 zi
2 miao
3 chumo
b 10
c 15
a 5

首次运行,ipairs一组未输出key-value形式数据,但输出了所有“单个”数据,pairs一组输出了所有数据。
多次运行,ipairs同上,pairs一组除“单个数据”输出顺序不变外,key-value形式数据输出顺序发生改变。

ipairs与pairs遍历杂表2

代码如下所示:

for i,v in ipairs(tableName) do
print("ipairs遍历杂表2");
for i,v in ipairs(testTab3) do
print(i,v);
end
print("pairs遍历杂表2");
for k,v in pairs(testTab3) do
print(k,v);
end

输出结果为:


ipairs遍历杂表2
1 zi
2 miao
pairs遍历杂表2
1 zi
2 miao
4 chumo
a 5
c 15
b 10

首次运行,ipairs一组同杂表1结果,但遇到nil(空)不再输出后面的数据。pairs同杂表1结果,且能越过nil继续输出后续值。
多次运行,ipairs一组结果不变,pairs一组结果除“单个数据”输出顺序不变外,key-value形式输出顺序发生改变。

分析与总结

由上结果分析,ipairs只能用来遍历“纯数组”类型的数据,对于key-value形式无能为力,且会根据“数组索引”按顺序输出。若遇到nil(空),则直接跳出循环。想必ipairs的全程也许是“index pairs”。
pairs能够用来遍历所有类型数据,且能够跳过nil继续输出后续值。同时它会按顺序输出“数组索引”类型数据,而后随机输出key-value类型数据。
这是为什么呢?转载来自csdn上tsbyj的解释:

这是因为table在存储值的时候是按照顺序的,但是在存储键值对的时候是按照键的哈希值存储的,并不会按照键的字母顺序或是数字顺序存储。
对于a来说,如果执行print(a[3]),输出的结果也会是Good。也就是说table并不会给键值对一个索引值。
也就是说ipairs只是按照索引值顺序,打印出了table中有索引值的数据,没有索引值的不管。
而pairs是先按照索引值打印,打印完成后再按照键值对的键的哈希值打印它的值。
http://blog.csdn.net/tsbyj/article/details/47302611

话说回来,三色绘恋又鸽了啊~残念……

引用资料

1、[头图]【www.lua.org】www.lua.org lua标志

梓喵出没博客(azimiao.com)版权所有,转载请注明链接:https://www.azimiao.com/2738.html
欢迎加入梓喵出没博客交流群:313732000

我来吐槽

*

*

0位绅士参与评论

  1. 岁月小筑11-21 20:15 回复

    咋又折腾起Lua来了,还有那个三色绘恋,为啥不开评论啊

    • 野兔11-21 20:57 回复

      因为三色绘恋还没更新……鸽子了

      • 岁月小筑11-21 22:06 回复

        哈哈哈哈哈哈哈哈哈哈哈哈哈哈哈哈哈哈哈哈