如何在Lua中检查两个表(对象)是否具有相同的值
2017-12-6 21:51:10
收藏:0
阅读:174
评论:6
我想在 Lua 中检查两个表是否具有相同的值,但没有找到方法。
我使用 == 运算符,它似乎只检查相同的对象,而不是表中的元素。
如果我有两个表,
a={}
b={}
a==b 的值为 false。
但如果
a={}
b=a
a==b 的值为 true。
我想知道是否有一种方法可以检查 Lua 中具有相同元素的两个表。是否有内置函数类似于 table.equals() 来检查?
点赞
用户1821558
顺便说一下,我检查了 @lhf 的链接,发现它已经失效了,我找到了这个有用的例子:
function is_table_equal(t1, t2, ignore_mt)
local ty1 = type(t1)
local ty2 = type(t2)
if ty1 ~= ty2 then return false end
-- 非table类型可以直接比较
if ty1 ~= 'table' and ty2 ~= 'table' then return t1 == t2 end
-- 也可以比较有__eq元方法的表
local mt = getmetatable(t1)
if not ignore_mt and mt and mt.__eq then return t1 == t2 end
for k1, v1 in pairs(t1) do
local v2 = t2[k1]
if v2 == nil or not is_table_equal(v1, v2) then return false end
end
for k2, v2 in pairs(t2) do
local v1 = t1[k2]
if v1 == nil or not is_table_equal(v1, v2) then return false end
end
return true
end
2015-06-10 13:12:03
用户178911
我对Rutrus的解决方案提出了一些改进建议。
function equals(o1, o2, ignore_mt)
if o1 == o2 then return true end
local o1Type = type(o1)
local o2Type = type(o2)
if o1Type ~= o2Type then return false end
if o1Type ~= 'table' then return false end
if not ignore_mt then
local mt1 = getmetatable(o1)
if mt1 and mt1.__eq then
--使用内置方法进行比较
return o1 == o2
end
end
local keySet = {}
for key1, value1 in pairs(o1) do
local value2 = o2[key1]
if value2 == nil or equals(value1, value2, ignore_mt) == false then
return false
end
keySet[key1] = true
end
for key2, _ in pairs(o2) do
if not keySet[key2] then return false end
end
return true
end
请注意,此解决方案不考虑自引用。您可以使用pequals(下方)处理这种情况,它在代码中非常有用。 但是不要在常规检查中使用此方法!它的速度较慢。另外,如果您的对象具有自引用,则应重新分析其结构。自引用可能是糟糕架构的标志。
local function internalProtectedEquals(o1, o2, ignore_mt, callList)
if o1 == o2 then return true end
local o1Type = type(o1)
local o2Type = type(o2)
if o1Type ~= o2Type then return false end
if o1Type ~= 'table' then return false end
--仅在对象为表时添加,缓存结果
local oComparisons = callList[o1]
if not oComparisons then
oComparisons = {}
callList[o1] = oComparisons
end
--false表示比较正在进行中
oComparisons[o2] = false
if not ignore_mt then
local mt1 = getmetatable(o1)
if mt1 and mt1.__eq then
--使用内置方法进行比较
return o1 == o2
end
end
local keySet = {}
for key1, value1 in pairs(o1) do
local value2 = o2[key1]
if value2 == nil then return false end
local vComparisons = callList[value1]
if not vComparisons or vComparisons[value2] == nil then
if not internalProtectedEquals(value1, value2, ignore_mt, callList) then
return false
end
end
keySet[key1] = true
end
for key2, _ in pairs(o2) do
if not keySet[key2] then
return false
end
end
--比较完成-对象相等,不要再比较
oComparisons[o2] = true
return true
end
function pequals(o1, o2, ignore_mt)
return internalProtectedEquals(o1, o2, ignore_mt, {})
end
您也可以分析Lua Wiki上的CompareTables。
2015-09-18 20:47:27
用户1142299
如果您真的想测试简单的表格,请尝试以下...
function do_tables_match( a, b )
return table.concat(a) == table.concat(b)
end
另外,有些与您的特定示例相比的内容如下...
function is_table_empty( table_to_test )
-- 不起作用
return table_to_test == {}
-- 仅在表格具有数字键而没有空隙的情况下起作用
return #table_to_test = 0
-- 起作用!
return next( table_to_test ) ~= nil
end
2019-01-11 03:53:37
用户10637463
我目前使用这个:
local tableCompare
do
-- 定义局部函数 compare
local compare
compare = function(src, tmp, _reverse)
if (type(src) ~= "table" or type(tmp) ~= "table") then
return src == tmp
end
for k, v in next, src do
if type(v) == "table" then
if type(tmp[k]) ~= "table" or not compare(v, tmp[k]) then
return false
end
else
if tmp[k] ~= v then
return false
end
end
end
return _reverse and true or compare(tmp, src, true)
end
-- 定义全局函数 tableCompare
tableCompare = function(src, tmp, checkMeta)
-- 调用 compare 函数,检查元表
return compare(src, tmp) and (not checkMeta or compare(getmetatable(src), getmetatable(tmp)))
end
end
-- 输出 true
print(tableCompare({ 1 , b = 30 }, { b = 30, 1 }, false))
2019-08-24 22:38:24
评论区的留言会收到邮件通知哦~
推荐文章
- 如何将两个不同的lua文件合成一个 东西有点长 大佬请耐心看完 我是小白研究几天了都没搞定
- 如何在roblox studio中1:1导入真实世界的地形?
- 求解,lua_resume的第二次调用继续执行协程问题。
- 【上海普陀区】内向猫网络招募【Skynet游戏框架Lua后端程序员】
- SF爱好求教:如何用lua实现游戏内调用数据库函数实现账号密码注册?
- Lua实现网站后台开发
- LUA错误显式返回,社区常见的规约是怎么样的
- lua5.3下载库失败
- 请问如何实现文本框内容和某个网页搜索框内容连接,并把网页输出来的结果反馈到另外一个文本框上
- lua lanes多线程使用
- 一个kv数据库
- openresty 有没有比较轻量的 docker 镜像
- 想问一下,有大佬用过luacurl吗
- 在Lua执行过程中使用Load函数出现问题
- 为什么 neovim 里没有显示一些特殊字符?
- Lua比较两个表的值(不考虑键的顺序)
- 有个lua简单的项目,外包,有意者加微信 liuheng600456详谈,最好在成都
- 如何在 Visual Studio 2022 中运行 Lua 代码?
- addEventListener 返回 nil Lua
- Lua中获取用户配置主目录的跨平台方法
没有预设函数用于比较表格的内容。
你需要自己编写。你需要决定是浅层比较还是深层比较表格内容。 可以参考https://web.archive.org/web/20131225070434/http://snippets.luacode.org/snippets/Deep_Comparison_of_Two_Values_3获取一些想法。