如何引用具有Lua中数字键值的表?

如何引用具有Lua中数字键值的表?,lua,Lua,以下脚本的输出为: AD[1] = [variable not found] AD['2'] = bar 如何修改函数getfield以在两种情况下都返回v值 function getfield (f) local v = _G for w in string.gfind(f, "[%w_]+") do v = v[w] end return v end AD = {[1] = 'foo', ['2'] = 'bar'} data = {"AD[1]","AD[

以下脚本的输出为:

AD[1] = [variable not found]
AD['2'] = bar
如何修改函数getfield以在两种情况下都返回v值

function getfield (f)
  local v = _G    
  for w in string.gfind(f, "[%w_]+") do
    v = v[w]
  end
 return v
end

AD = {[1] = 'foo', ['2'] = 'bar'}
data = {"AD[1]","AD['2']"}

for i,line in ipairs(data) do
  s = getfield(line)
  if s then
        print(line .. " = " .. s)
  else 
    print(line .. " = [variable not found]")
  end
end
更新: 我90%肯定,这对我来说是可行的:

function getfield (f)
  local v = _G    
    for w in string.gfind(f, "['%w_]+") do
      if (string.find(w,"['%a_]")==nil) then
        w = loadstring('return '..w)()
      else 
        w = string.gsub(w, "'", "") 
      end
      v=v[w]
  end
  return v
end

您将获得字符串
'1'
“'2'
。您必须对其进行评估,以将其转化为任何对象:

v = v[loadstring('return ' .. w)()]
但是,如果字符串来自不受信任的源(如用户输入或其他),则不要这样做,因为它们可能执行任意代码。

这种情况正好有效

function getfield (f)
  local v = _G    
  for w in string.gfind(f, "['%w_]+") do
    local x = loadstring('return '..w)()
    print(w,x)
    v = v[x] or v[w]
  end
 return v
end

AD = {[1] = 'foo', ['2'] = 'bar'}
data = {"AD[1]","AD['2']"}

for i,line in ipairs(data) do
  s = getfield(line)
  if s then
        print(line .. " = " .. s)
  else 
    print(line .. " = [variable not found]")
  end
end
但它很脆弱

注意,我在模式中添加了

困难在于,有时w是一个表示名称(键)的字符串,有时它是一个表示数字的字符串。在第二种情况下,它需要从字符串转换为数字。但是您需要上下文或一些语法来决定

这就是我所说的脆弱性:

>     data = {"math[pi]","AD['2']"}
>     
>     for i,line in ipairs(data) do
>>       s = getfield(line)
>>       if s then
>>             print(line .. " = " .. s)
>>       else 
>>         print(line .. " = [variable not found]")
>>       end
>>     end
math    table: 0x10ee05100
pi  nil
math[pi] = 3.1415926535898
AD  table: 0x10ee19ee0
'2' 2
AD['2'] = bar


> pi = 3
> math[3] = 42
>     data = {"math[pi]","AD['2']"}>
>     for i,line in ipairs(data) do
>>       s = getfield(line)
>>       if s then
>>             print(line .. " = " .. s)
>>       else 
>>         print(line .. " = [variable not found]")
>>       end
>>     end
math    table: 0x10ee05100
pi  3
math[pi] = 42
AD  table: 0x10ee19ee0
'2' 2
AD['2'] = bar

math[pi]
是不变的,但是
getfield
在全局上下文中解释pi并获取
3
,因此返回了错误的
math
字段。

尝试索引局部'v'(一个零值)@shaun5这是原始代码中的问题;您将
v
设置为
\u G
,然后将其设置为
\u G
的索引,然后将其设置为索引的索引,此时它将变为
nil
。你想做什么?见附录“我是说脆弱性……”我想不出一个让它失败的方案。我原以为:AD={[1]='foo',['1']='foobar',['2']='bar'}可以做到,但仍然有效。。这个场景是什么?我在回答的最后展示了一个场景,当一个键在_G中有一个值时。那么,是使用_G中键的值,还是使用键的文本,这是不明确的。如果您允许嵌套表,则在表的下一级可能会出现相同的问题。嵌套表方案是什么?可能没有嵌套表方案,因为
loadstring
始终在_G中计算。