Указание обоих методов и оператора индекса в метатаблице Lua

Мне нужны объекты пользовательских данных для поддержки обоих методов и оператора индекса (с целочисленными индексами). Есть ли способ добиться этого в общей метатаблице без моделирования методов с помощью функции?

Я попытался объединить метатаблицы в цепочку, установив metatable(object).__index для таблицы с фактическими методами и metatable(metatable(object).__index).__index для функции, реализующей оператор индекса. Однако эта функция вызывается с первой __index таблицей в качестве аргумента вместо исходного объекта. Это похоже на упущение в дизайне, поскольку гораздо больше смысла передавать исходный объект, когда __index метаметод является функцией. В любом случае, есть ли способ добиться того, чего я хочу, без явной проверки имен методов в функции __index?


person riv    schedule 03.05.2014    source источник


Ответы (2)


Вы можете использовать одну функцию __index, которая одновременно обращается к таблице методов и обрабатывает целочисленные ключи.

function metatable:__index(key)
  if type(key) == 'string' then
    return methodTable[key]
  elseif type(key) == 'number' then
    return key * 42 + #self
  end
end
person luther    schedule 04.05.2014

Когда вы устанавливаете __index в таблицу, Lua автоматически выполняет обычный поиск ключа в таблице __index. Он полностью эквивалентен debug.getmetatable(obj).__index[k] и будет выполнять рекурсивный __index поиск или вызов функции, если таблица __index имеет свою собственную __index таблицу.

person Colonel Thirty Two    schedule 03.05.2014