Вопрос возник из http://tylerneylon.com/a/learn-lua/ учебника. включает коды:
Dog = {dog1 = 'original dog class'}
function Dog.new(self, ... )
newObj = {sound = 'woof'}
self.__index = self
return setmetatable(newObj, self)
end
function Dog.makeSound(self, ... )
print('I say' .. self.sound)
end
print('Dog=', Dog)
print('Dog.metatable=', getmetatable(Dog)) -- this will output nothing
myDog = Dog.new(Dog)
print('\nmyDog=', myDog)
print('myDog.metatable=', getmetatable(myDog))
myDog.makeSound(myDog)
Это результат приведенных выше кодов в учебнике:
wirelessprvnat-172-17-106-141:Programming frankhe$ th test2.lua
Dog= {
makeSound : function: 0x0a6cec20
dog1 : "original dog class"
new : function: 0x0a6cec00
}
Dog.metatable= nil
myDog= {
sound : "woof"
}
myDog.metatable= {
makeSound : function: 0x0a6cec20
__index :
{
makeSound : function: 0x0a6cec20
__index :
{
makeSound : function: 0x0a6cec20
__index :
{
makeSound : function: 0x0a6cec20
__index :
{
makeSound : function: 0x0a6cec20
__index : {...}
dog1 : "original dog class"
new : function: 0x0a6cec00
}
dog1 : "original dog class"
new : function: 0x0a6cec00
}
dog1 : "original dog class"
new : function: 0x0a6cec00
}
dog1 : "original dog class"
new : function: 0x0a6cec00
}
dog1 : "original dog class"
new : function: 0x0a6cec00
}
I saywoof
Одна дополнительная фотография для более четкого изображения вопроса
Хотя реализация в учебнике успешно печатает «I saywoof», метатаблица myDog, по-видимому, не так желательна, как мы ожидали. Поэтому мое решение ниже (различия в Dog.new):
function Dog.new(self, ... )
newObj = {sound = 'woof'}
return setmetatable(newObj, {__index = self})
end
Результат моего решения:
wirelessprvnat-172-17-106-141:Programming frankhe$ th test2.lua
Dog= {
makeSound : function: 0x0d7f2978
dog1 : "original dog class"
new : function: 0x0d7f2958
}
Dog.metatable= nil
myDog= {
sound : "woof"
}
myDog.metatable= {
__index :
{
makeSound : function: 0x0d7f2978
dog1 : "original dog class"
new : function: 0x0d7f2958
}
}
I saywoof
Мой код печатает «I saywoof» и имеет более точную структуру таблицы. Я хочу знать, какая реализация правильная, та, что в учебнике, или моя? Кроме того, я хочу знать, почему код в учебнике генерирует итеративное определение метатаблицы Dog.
print
функция производит этот вывод? Я не верю, что это правильная иерархия. Я считаю, что ваше изменение просто создает новую таблицу каждый раз, когда вызываетсяDog:new()
, а не повторное использование существующей таблицыDog
. (Хотя я согласен с тем, чтоself.__index = self
в функцииnew
является странным, поскольку вам действительно нужно сделать это только один раз для каждого класса (а не один раз для каждого экземпляра, посколькуself
является классом). - person Etan Reisner   schedule 09.05.2016Print
— это просто функция печати по умолчанию в lua. - person Frank He   schedule 09.05.2016Dog.new
и повторно использовать ее. - person siffiejoe   schedule 09.05.2016print
не печатает такие таблицы. Ах,th
, похоже, интерпретатор факела с настраиваемой функциейprint
. И я считаю, что это просто сбивает с толку таблица, имеющая себя как__index
и возвращающаяся к своей максимальной глубине четыре. Если вы вызоветеsetprintlevel
, чтобы изменить это значение, держу пари, вы увидите, что он напечатает ровно столько вложенных уровней, сколько вы установили для печати. - person Etan Reisner   schedule 09.05.2016