"t1.__index = t2" 和 "setmetatable(t1, {__index = t2})" 有什么区别?

What's difference between "t1.__index = t2" and "setmetatable(t1, {__index = t2})"?

我在别人的代码里看到过这个东西,如果我没看错的话应该是这样使用的:

t1 = {}
t1.__index = t2 --1

function t1:new()
    local new = {}
    setmetatable(new, {__index = t1}) --2

    new.something = 0

    return new
end

但是他们到底是干什么的,为什么会有不同的写法呢?

它们的写法不同,因为它们做的事情不同。

t1 = {}
t2 = {a = 20}
meta = {__index = t2}
setmetatable(t1, meta)
print(t1.a) -- prints 20

注意这里有 3 个 table:meta,metatable,t2,它存储密钥 at1 我们要设置它来查找 t2.

中丢失的键

metatable 仅用于控制 t1 行为的目的,但是,为了减少 table 的使用,人们经常使用后备 table( t2) 作为元table (meta) 所以它变成了类似

t1 = {}
t2_and_meta = {a = 20}
t2_and_meta.__index = t2_and_meta
setmetatable(t1, t2_and_meta)
print(t1.a) -- prints 20