Objekte ausgeben
Wenn du ein Objekt ausgibst, print(karotte), weiß Lua nicht, was daran wichtig ist. Es gibt table: und die Adresse der Tabelle im Speicher des Computers aus, etwa table: 0x109010, und das sagt dir nicht viel. Die Metamethode __tostring behebt das. Sie ist eine Funktion, die das Objekt bekommt und einen Text zurückgibt, und print und tostring benutzen diesen Text:
local Pflanze = {}
Pflanze.__index = Pflanze
function Pflanze.new(name, tage)
local pflanze = {name = name, tage = tage, alter = 0}
setmetatable(pflanze, Pflanze)
return pflanze
end
function Pflanze:wachsen()
self.alter = self.alter + 1
end
function Pflanze:__tostring()
if self.alter >= self.tage then
return self.name .. " (reif)"
end
return self.name .. " (Tag " .. self.alter .. " von " .. self.tage .. ")"
end
local feld = {Pflanze.new("Weizen", 2), Pflanze.new("Karotte", 3), Pflanze.new("Kürbis", 7)}
for tag = 1, 2 do
for _, pflanze in ipairs(feld) do
pflanze:wachsen()
end
end
for _, pflanze in ipairs(feld) do
print(pflanze)
end
print("Erste Pflanze auf dem Feld: " .. tostring(feld[1]))Das gibt Folgendes aus:
Weizen (reif)
Karotte (Tag 2 von 3)
Kürbis (Tag 2 von 7)
Erste Pflanze auf dem Feld: Weizen (reif)Pflanze ist die Metatabelle jeder Pflanze, also funktioniert ein __tostring in Pflanze für alle. Du schreibst es wie jede andere Methode, und self ist die Pflanze, die es beschreiben soll: function Pflanze:__tostring() bedeutet Pflanze.__tostring = function(self). Darin kannst du alles tun, was eine Methode kann, zum Beispiel prüfen, ob die Pflanze reif ist. Lua ruft es für dich auf, wenn es das Objekt als Text braucht: in print, in tostring und für %s in string.format, sodass string.format("%s!", feld[1]) den Text Weizen (reif)! ergibt.
Typische Fehler:
- Verbinden mit
... Der Operator..benutzt__tostringnicht. Wennkarotteeine Pflanze ist, endet"Auf dem Feld: " .. karottemitattempt to concatenate a table value (local 'karotte'). Wandle das Objekt zuerst mittostring(karotte)in einen Text um, wie in der letzten Zeile des Beispiels. - Ausgeben statt zurückgeben.
__tostringmuss den Text mitreturnzurückgeben. Wenn es den Text ausgibt und nichts zurückgibt, endet das Programm mit dem Fehler'__tostring' must return a string.
So schreibst du es:
Anweisungen
- 1
Führe das Programm aus: Es gibt das Huhn als
table:und eine Adresse aus. FügeHuhndie Metamethode__tostringhinzu, sodassprint(goldi)Folgendes ausgibt:Goldi (2 Eier) - 2
Gib darunter die Zeile
Bestes Huhn: Goldi (2 Eier)aus. Baue sie mit..aus dem Huhn selbst,goldi, nicht aus einem Text, den du ausschreibst.Goldi (2 Eier) Bestes Huhn: Goldi (2 Eier) - 3
Perle hat nur ein einziges Ei gelegt, und
Perle (1 Eier)wäre falsch. Ändere__tostringso, dass esEischreibt, wenn das Huhn genau 1 Ei hat. Erzeuge Perle mitHuhn.new, lass sie 1 Ei legen und gib sie unter den anderen Zeilen aus:Goldi (2 Eier) Bestes Huhn: Goldi (2 Eier) Perle (1 Ei)