Configuration 如何防止更改指定的表内容?

Configuration 如何防止更改指定的表内容?,configuration,static,lua,serial-port,lua-table,Configuration,Static,Lua,Serial Port,Lua Table,我在为微控制器编写端口处理例程时得到了这个(非常简化的)场景。 3个文件 文件1: table = {var1 = true, var2 = true, var 3 = false, var 4 = true} function dosomething() dosomething --defines bools in table by whatever condition is present end 实际上是菜单。如果给定一个输入,表中相应的布尔值将更改 function s

我在为微控制器编写端口处理例程时得到了这个(非常简化的)场景。 3个文件

文件1:

table = {var1 = true, var2 = true, var 3 = false, var 4 = true}
function dosomething()
    dosomething
    --defines bools in table by whatever condition is present
end
实际上是菜单。如果给定一个输入,表中相应的布尔值将更改

function selection()
     selection = interprete_input()
     invertVars(selection)
end

function invertVars(selection)
         table.selection = not table.selection
 end
文件3:在简化场景中,仅使用bools@table知道它是否适用于给定的情况。索引也用作值。例如,表中的一个条目可能是“[“ttyS0”]=true”,因此我知道该函数是否应该为COM端口ttyS0运行

function needsVarsFromTable()
    for v,k in pairs(table)
        if k then
            --the actual function uses true/false as indicator to know if to run 
            --for  the entry of table or not.
            the_actual_function_that_needs_v(v)
        end
end
现在的问题是:

该表包含19个条目。其中2个必须是静态的。它们是假的,永远不会是真的。但在我的脚本中,有可能使它们成为真的,这将导致错误

不幸的是,Lua没有带来静态变量。如何防止它们被其他功能更改?这些其他函数仍然必须能够读取它们

我不想每次都检查var@Table如果由于性能问题允许更改读取函数。

提供了只读表的示例,如果您不熟悉元表和元方法,请阅读整个章节

为了保护字段
“var2”
,对本书中的代码稍加修改即可:

local t = {var1 = true, var2 = true, var3 = false, var4 = true}

function protect_field(t)
    local proxy = {}
    local mt = { -- create metatable
    __index = t,
    __newindex = function (t, k, v)
        if k == 'var2' then
            error("attempt to update var2 field")
        else
            rawset(t, k, v)
        end
    end
    }
    setmetatable(proxy, mt)
    return proxy
end

t = protect_field(t)
现在可以合法地更新字段
“var1”

但是
t.var2=false
将引发错误。

提供了一个只读表的示例,如果您不熟悉元表和元方法,请阅读整个章节

为了保护字段
“var2”
,对本书中的代码稍加修改即可:

local t = {var1 = true, var2 = true, var3 = false, var4 = true}

function protect_field(t)
    local proxy = {}
    local mt = { -- create metatable
    __index = t,
    __newindex = function (t, k, v)
        if k == 'var2' then
            error("attempt to update var2 field")
        else
            rawset(t, k, v)
        end
    end
    }
    setmetatable(proxy, mt)
    return proxy
end

t = protect_field(t)
现在可以合法地更新字段
“var1”

但是
t.var2=false
将引发错误。

提供了一个只读表的示例,如果您不熟悉元表和元方法,请阅读整个章节

为了保护字段
“var2”
,对本书中的代码稍加修改即可:

local t = {var1 = true, var2 = true, var3 = false, var4 = true}

function protect_field(t)
    local proxy = {}
    local mt = { -- create metatable
    __index = t,
    __newindex = function (t, k, v)
        if k == 'var2' then
            error("attempt to update var2 field")
        else
            rawset(t, k, v)
        end
    end
    }
    setmetatable(proxy, mt)
    return proxy
end

t = protect_field(t)
现在可以合法地更新字段
“var1”

但是
t.var2=false
将引发错误。

提供了一个只读表的示例,如果您不熟悉元表和元方法,请阅读整个章节

为了保护字段
“var2”
,对本书中的代码稍加修改即可:

local t = {var1 = true, var2 = true, var3 = false, var4 = true}

function protect_field(t)
    local proxy = {}
    local mt = { -- create metatable
    __index = t,
    __newindex = function (t, k, v)
        if k == 'var2' then
            error("attempt to update var2 field")
        else
            rawset(t, k, v)
        end
    end
    }
    setmetatable(proxy, mt)
    return proxy
end

t = protect_field(t)
现在可以合法地更新字段
“var1”


但是
t.var2=false
将引发错误。

好的,但是,
rawset(t,“var2”,“can,too”)
@TomBlodget将只在代理表中设置它。不是原始表格。@daurnimator很好。但它仍然是模糊的安全性:
rawset(getmetatable(t)。\uu索引,“var2”,“can,too”)
。该技术适用于表示只读意图。如果您担心这一点,请设置
\uuuu metatable
,并且不要向任何人授予对
debug.getmetatable
的访问权限。但是,在这一点上,人们只是故意开枪打自己的脚。好吧,但是,
rawset(t,“var2”,“can,too”)
@TomBlodget,它只会在代理表中设置它。不是原始表格。@daurnimator很好。但它仍然是模糊的安全性:
rawset(getmetatable(t)。\uu索引,“var2”,“can,too”)
。该技术适用于表示只读意图。如果您担心这一点,请设置
\uuuu metatable
,并且不要向任何人授予对
debug.getmetatable
的访问权限。但是,在这一点上,人们只是故意开枪打自己的脚。好吧,但是,
rawset(t,“var2”,“can,too”)
@TomBlodget,它只会在代理表中设置它。不是原始表格。@daurnimator很好。但它仍然是模糊的安全性:
rawset(getmetatable(t)。\uu索引,“var2”,“can,too”)
。该技术适用于表示只读意图。如果您担心这一点,请设置
\uuuu metatable
,并且不要向任何人授予对
debug.getmetatable
的访问权限。但是,在这一点上,人们只是故意开枪打自己的脚。好吧,但是,
rawset(t,“var2”,“can,too”)
@TomBlodget,它只会在代理表中设置它。不是原始表格。@daurnimator很好。但它仍然是模糊的安全性:
rawset(getmetatable(t)。\uu索引,“var2”,“can,too”)
。该技术适用于表示只读意图。如果您担心这一点,请设置
\uuuu metatable
,并且不要向任何人授予对
debug.getmetatable
的访问权限。但在这一点上,人们只是故意朝自己的脚开枪。