从Lua中的表中删除元表

从Lua中的表中删除元表,lua,garbage,metatable,Lua,Garbage,Metatable,我想从表中“解开”一个元表,我想知道: tbl = setmetatable(tbl, false) -- or nil 这样做正确吗?我找不到有关如何正确操作的任何信息。我需要使用赋值运算符吗 此外,如果元表没有引用且是匿名的,那么这是否足以销毁附加到该表的元表 tbl = setmetatable({}, {__index = something}) -- later on: tbl = nil 垃圾收集器足以删除这两个表吗?根据Lua参考,在这里提出问题之前,您应该经常查阅该参考,se

我想从表中“解开”一个元表,我想知道:

tbl = setmetatable(tbl, false) -- or nil
这样做正确吗?我找不到有关如何正确操作的任何信息。我需要使用赋值运算符吗

此外,如果元表没有引用且是匿名的,那么这是否足以销毁附加到该表的元表

tbl = setmetatable({}, {__index = something})
-- later on:
tbl = nil

垃圾收集器足以删除这两个表吗?

根据Lua参考,在这里提出问题之前,您应该经常查阅该参考,
setmetatable(tbl,nil)
将删除table
tbl
的元表,除非tbl的原始元表受到保护。或者我们最好说它不删除元表,而是删除对它的引用。当然,只要有其他引用,充当元表的表就不会被删除

在询问人们一个简单的函数调用是否有效之前,请自己尝试一下。 您可以使用或任何其他Lua解释器,在不涉及任何其他人的情况下在几秒钟内得到答案

运行此代码:

setmetatable({}, false)

将导致

输入:1:setmetatable的错误参数#2(应为nil或table)

现在您知道不能输入false,必须显式输入nil

要检查参考手册中的_u图元表,您可以尝试以下代码

local tbl = setmetatable({}, {__metatable = true})
setmetatable(tbl, nil)
这将导致以下输出:

输入:2:无法更改受保护的元表

关于你问题的第二部分:

tbl=nil不会删除tbl引用的表。它只会删除对它的引用tbl

local a = {}
local b = a
b = nil
print(a)
a仍然是一张桌子。您只删除了其中一个引用

一旦没有剩余的引用,垃圾收集器就可以收集表

setmetatable(tbl,{})
将建立对表构造函数
{}
返回的表的引用,并将该引用存储在
tbl
的内部某处

如果
tbl
是对该表的最后一次引用,那么它将在某个时候作为垃圾收集。当然,对设置为metatable的表的唯一引用也将消失,并且也将被删除

如果您这样做:

local a = {}
local b = setmetatable({}, a)
,,
a=nil
不会删除b的元表


因此,如果没有对其中任何一个表的其他引用,它将删除这两个表。

nil应该可以,它不会接受false.,值得指出的是,如果开发人员确实通过设置
\uu metatable
来保护元表,那么如果
debug.getmetatable
存在,您仍然可以得到它(或者如果您能够自己在调试库中加载)-否则您必须通过C API来完成
local a = {}
local b = setmetatable({}, a)