local metatbl = {}
metatbl.tbls = {mL, mM};
function metatbl.__index(intbl, key)
for i, mtbl in ipairs(metatbl.tbls) do
local mmethod = mtbl.__index
if(type(mmethod) == "function") then
local ret = mmethod(table, key)
if ret then return ret end
else
if mmethod[key] then return mmethod[key] end
end
return nil
end
end
setmetatable(_G,metatbl)
combined_metatable = {
__index = function (t, k)
return mL.__index (t, k) or mM.__index (t, k)
end
}
setmetatable (_G, combined_metatable)
这样做的好处是不会摆弄 mL 或 mM 本身 .
如果您事后没有机会更正事项,您只需修改库元表的 __index 条目即可进行组合搜索:
local original_mM_index = mM.__index
local original_mL_index = mL.__index
local function L_then_M_index (t, k)
return original_mL_index (t, k) or original_mM_index (t, k)
end
mL.__index = L_then_M_index
mM.__index = L_then_M_index
getmetatable(getfenv()).__metatable = function ( o ) return { } end
要么
local orig_setmetatable = setmetatable
function setmetatable ( ob , mt )
if ob == getfenv() or ob == _G then
return ob
else
return orig_setmetatable(ob,mt)
end
end
local env_indexes = {}
setmetatable(_G,{__index=function(t,k) for i,m in ipairs(env_indexes) do local v=m[k]; if v then return v end end return nil end } )
local orig_setmetatable = setmetatable
function setmetatable ( ob , mt )
if ob == _G then
table.insert ( env_indexes , mt.__index )
return ob
else
return orig_setmetatable(ob,mt)
end
end
3 回答
有一个metatable存储
mL
和mM
,如果有一个返回nil
,请检查另一个:假设你的代码可以摆弄
_G
的metatable本身,在库已经破解之后,为了解决L和M所做的事情,你可以坚持使用你自己的metatable进行组合搜索,例如:这样做的好处是不会摆弄
mL
或mM
本身 .如果您事后没有机会更正事项,您只需修改库元表的
__index
条目即可进行组合搜索:[请注意,由于两个库元表都被修改,这将适用于最后安装的任何一个(“赢得”竞争) .
使用__metatable为它们提供一个实际上不是metatable的表,或者为库提供不同的setmetatable:这样他们就无法更改_G metatable .
要么
(取决于图书馆的工作方式)
如果你仍然想跟踪它对metatable所做的事情;在返回ob之前查看mt(如果你真的想链接__index查找;添加到表中):
否则这对于图书馆来说是非常糟糕的做法;告诉作者不要!