Как вы ссылаетесь на таблицу с числовым значением ключа в Lua? - PullRequest
0 голосов
/ 18 февраля 2012

Вывод для приведенного ниже сценария:

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

UPDATE: Я уверен на 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

Ответы [ 2 ]

1 голос
/ 18 февраля 2012

Это работает

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

, но довольно хрупко.

Обратите внимание, что я добавил ' к шаблону.

Сложность в том, что иногдаэто строка, представляющая имя (ключ), а иногда это строка, представляющая число.Во втором случае его необходимо преобразовать из строки в число.Но вам нужен контекст или некоторый синтаксис, чтобы решить.

Вот такой тип хрупкости, который я имею в виду:

>     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.

0 голосов
/ 18 февраля 2012

Вы получите строки '1' и "'2'". Вы должны оценить его, чтобы превратить его в любой объект:

v = v[loadstring('return ' .. w)()]

Не делайте этого, если строка получена из ненадежного источника (например, пользовательский ввод или что-то в этом роде), поскольку они могут выполнять произвольный код.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...