lua中统计数表数据两个方法及其优劣
现在有一个需求: 针对一个答题统计, 需要统计近5次的错误次数.
思路是, 使用数表去储存这5次错误次数, 然后统计数表
现在有一个5个元素的数表 error_last_5_times = {1, 0, 1, 0 ,1}
其中1表示正确, 0表示错误
这里有两种统计方法:
-- 方法1: 使用迭代数表来统计
error_last_5_times = {1, 0, 1, 0 ,1}
total1 = function (error_last_5_times)
local wrong_times = 0
for i = 1, 5 do
if error_last_5_times[i] == 0 then
wrong_times = wrong_times + 1
end
end
return wrong_times
end
-- 方法2: 使用字符串统计
error_last_5_times = {1, 0, 1, 0 ,1}
total2 = function (error_last_5_times)
local _, wrong_times
-- 将数表转化为字符串, 统计替换字符串中"0"的次数
_, wrong_times = table.concat(error_last_5_times, ""):gsub("0", "")
return wrong_times
end
通常而言, total1
函数会更快一些, 但是可读性上不是很好.
total2
函数因为使用到了两个内置函数( table.concat
和 string.gsub
)去处理, 可读性上会更高, 但是效率会稍微差上一些, 这一点点出来之后稍微回看一下代码就可以比较清楚的理解了.
还有一个新的需求: 因为是一个答题模拟, 所以不断地有新的数据传入, 需要将新数据答题的正确或者错误, 写入 error_last_5_times
这个表中, 但是需要统计的还是近5次的错误次数.
也就是, 需要一个添加新数据的函数.
一样的, 我们看两个函数:
-- 方法1: 使用循环缓存结构去添加新数据
-- 在`error_last_5_times`表中添加一个键`index`, 用来缓存循环数
error_last_5_times = {1, 0, 1, 0 ,1 , index = 0}
add1 = function (error_last_5_times, value)
-- 使用余数进行限制循环
error_last_5_times.index = (error_last_5_times.index % 5) + 1
error_last_5_times[error_last_5_times.index] = value
return error_last_5_times
end
在上面这个方法中, 使用了一个循环缓存结构去添加新数据, 即 error_last_5_times.index
是一个从1~5逐步循环的数, 当超过6的数出现时, 会回滚到前面的索引并覆盖原来的数据, 这使得添加新数据并不需要很高的运算.
-- 方法2: 使用内置表操作函数去添加新数据
error_last_5_times = {1, 0, 1, 0 ,1}
add2 = function (error_last_5_times, value)
table.insert(error_last_5_times, 1, value)
table.remove(error_last_5_times)
return error_last_5_times
end
在这一个方法中, 每次添加新数据, 会使用 table.inset
在 error_last_5_times
的第一个元素添加新的正确率数据, 并使用 table.remove
删除最后一个数据, 由于Lua中移动表的效率较低, 所以很明显, 这也是一个增加可读性以减少程序效率的方法.