English | 简体中文 | 繁體中文 | Русский язык | Français | Español | Português | Deutsch | 日本語 | 한국어 | Italiano | بالعربية
In Lua-Tabellen können wir die entsprechenden Schlüssel verwenden, um Werte zu erhalten, aber wir können zwei Tabellen nicht operieren.
Daher bietet Lua Metatables an, um das Verhalten von Tabellen zu ändern, wobei jedes Verhalten einem entsprechenden Metamethoden zugeordnet ist.
Zum Beispiel können wir mit Metatables definieren, wie Lua die Addition von zwei Tabellen berechnet.+b.
Wenn Lua versucht, zwei Tabellen zu addieren, überprüft es zuerst, ob eine der beiden Tabellen einen Metatable hat, und dann überprüft es, ob es ein Feld namens "__add" gibt. Wenn es gefunden wird, wird der entsprechende Wert aufgerufen. "__add"-Felder sind sofort und deren Werte (meistens eine Funktion oder eine Tabelle) sind "Metamethoden".
Es gibt zwei sehr wichtige Funktionen, um Metatables zu verarbeiten:
setmetatable(table, metatable): Setze den Metatable (metatable) für die angegebene Tabelle, wenn im Metatable (metatable) der Schlüssel __metatable existiert, wird setmetatable fehlschlagen.
getmetatable(table): Rückgabeobjekt Metatable (metatable).
Nachfolgender Beispiel zeigt, wie man einem bestimmten Tisch einen Metatable setzt:
mytable = {} -- Regulärer Tisch mymetatable = {} -- Metatable setmetatable(mytable, mymetatable) -- Setze mymetatable als Metatable von mytable
Der obige Code kann auch in einer Zeile direkt geschrieben werden:
mytable = setmetatable({}, {})
Hier ist das Rückgabeobjekt Metatable:
getmetatable(mytable) -- Das gibt zurück mymetatable
Das ist der häufigste Schlüssel im Metatable.
Wenn du eine Tabelle über einen Schlüssel abrufst und dieser Schlüssel keinen Wert hat, sucht Lua nach dem __index-Schlüssel im Metatable der Tabelle (angenommen, es gibt einen Metatable). Wenn __index eine Tabelle enthält, sucht Lua in dieser Tabelle nach dem entsprechenden Schlüssel.
Wir können den Interaktionsmodus mit dem lua-Befehl betreten und ansehen:
$ lua Lua 5.3.0 Copyright (C) 1994-2015 Lua.org, PUC-Rio > other = { foo = 3 } > t = setmetatable({}, { __index = other }) > t.foo 3 > t.bar nil
Wenn __index eine Funktion enthält, ruft Lua diese Funktion auf und überträgt die Tabelle und den Schlüssel als Parameter an die Funktion.
__index-Metamethode überprüft, ob das Element in der Tabelle existiert, wenn nicht existiert, wird der Rückgabewert nil sein; wenn existiert, wird der Rückgabewert von __index zurückgegeben.
mytable = setmetatable({key1 = "Wert"1"}, { __index = function(mytable, key) if key == "key2" then return "metatablevalue" else return nil end end ) print(mytable.key1,mytable.key2)
Beispiel-Ausgabeergebnis:
value1 metatablevalue
Beispielanalyse:
mytable-Tabelle zugewiesen {key1 = "value1"}。
mytable hat eine Metatabelle eingerichtet, die Metamethode ist __index.
In der mytable-Tabelle nach key suchen1,wenn gefunden, wird das Element zurückgegeben, wenn nicht gefunden, wird fortgesetzt.
In der mytable-Tabelle nach key suchen2,wenn gefunden, wird metatablevalue zurückgegeben, wenn nicht gefunden, wird fortgesetzt.
Überprüfen Sie, ob die Metatabelle __index hat, wenn __index eine Funktion ist, wird diese Funktion aufgerufen.
In der Metamethode überprüfen, ob "key2" Schlüsselparameter (mytable.key2Bereits gesetzt),wenn "key2" Parameter wird "metatablevalue" zurückgegeben, andernfalls wird der Wert des mytable entsprechenden Schlüssels zurückgegeben.
Wir können den obigen Code einfach schreiben:
mytable = setmetatable({key1 = "Wert"1"}, { __index = { key2 = "metatablevalue" } }) print(mytable.key1,mytable.key2)
Zusammenfassung
Die Regeln für die Suche nach einem Tabellenelement in Lua sind im Grunde wie folgt 3 Schritte:
1.Suchen Sie in der Tabelle, wenn Sie das Element finden, wird es zurückgegeben, wenn nicht gefunden, wird fortgesetzt
2.Überprüfen Sie, ob die Tabelle eine Metatabelle hat, wenn keine Metatabelle vorhanden ist, wird nil zurückgegeben, wenn eine Metatabelle vorhanden ist, wird fortgesetzt.
3.Überprüfen Sie, ob die Metatabelle __index hat, wenn __index eine nil ist, wird nil zurückgegeben; wenn __index eine Tabelle ist, wird wiederholt 1、2、3;wenn die __index-Methode eine Funktion ist, wird der Rückgabewert dieser Funktion zurückgegeben.
Dieser Teil des Inhalts stammt von dem Autor Huanzi: https://blog.csdn.net/xocoder/article/details/9028347
__newindex-Metamethode wird verwendet, um Tabellen zu aktualisieren, während __index zur Abrufung von Tabellen verwendet wird.
Wenn Sie einem fehlenden Index einer Tabelle einen Wert zuweisen, sucht der Interpreter nach der __newindex-Metamethode: Wenn diese Methode existiert, wird sie aufgerufen, ohne dass eine Zuweisung durchgeführt wird.
Nachfolgender Beispiel zeigt die Anwendung der __newindex-Metamethode:
mymetatable = {} mytable = setmetatable({key1 = "Wert"1"}, { __newindex = mymetatable }) print(mytable.key1) mytable.newkey = "neuer Wert"2" print(mytable.newkey, mymetatable.newkey) mytable.key1 = "neuer Wert"1" print(mytable.key1,mymetatable.key1)
Das Ausgaberesultat des obigen Beispiels ist:
value1 nil neuer Wert2 neuer Wert1 nil
In diesem Beispiel wurde die Tabelle den Metamethoden __newindex zugeordnet, bei der Zuweisung neuer Indexschlüssel (mytable.newkey = "neuer Wert2wird aufgerufen, ohne eine Zuweisung durchzuführen. Und wenn ein bestehender Indexschlüssel (key1) wird eine Zuweisung durchgeführt, ohne den Metamethoden __newindex aufzurufen.
Nachfolgender Beispiel zeigt die Verwendung der Funktion rawset, um die Tabelle zu aktualisieren:
mytable = setmetatable({key1 = "Wert"1"}, { __newindex = function(mytable, key, value) rawset(mytable, key, "\""..value.."\"") end ) mytable.key1 = "neue Wert" mytable.key2 = 4 print(mytable.key1,mytable.key2)
Das Ausgaberesultat des obigen Beispiels ist:
neue Wert "4"
Nachfolgender Beispiel zeigt die Zusammenführung der beiden Tabellen:
-- Berechnen Sie den größten Wert im Array, table.maxn in Lua5.2Diese Version kann nicht mehr verwendet werden -- Definieren Sie die benutzerdefinierte Funktion table_maxn, um die Anzahl der Elemente in der Tabelle zu berechnen function table_maxn(t) local mn = 0 for k, v in pairs(t) do if mn < k then mn = k end end return mn end -- Zusammenführung der beiden Tabellen mytable = setmetatable({ 1, 2, 3 }, { __add = function(mytable, newtable) for i = 1, table_maxn(newtable) do table.insert(mytable, table_maxn(mytable)+1,newtable[i]) end return mytable end ) secondtable = {4,5,6} mytable = mytable + secondtable for k, v in ipairs(mytable) do print(k, v) end
Das Ausgaberesultat des obigen Beispiels ist:
1 1 2 2 3 3 4 4 5 5 6 6
__add Schlüssel enthält die Metatabelle und führt die Addition durch. Die zugehörige Liste der Operationen in der Tabelle ist wie folgt: (Hinweis:__ist zwei Unterstriche)
Muster | Beschreibung |
---|---|
__add | entspricht dem Operator ''+' |
__sub | entspricht dem Operator ''-' |
__mul | entspricht dem Operator ''*' |
__div | entspricht dem Operator ''/' |
__mod | entspricht dem Operator '%'. |
__unm | entspricht dem Operator ''-' |
__concat | entspricht dem Operator '..'. |
__eq | entspricht dem Operator '=='. |
__lt | entspricht dem Operator '<'. |
__le | entspricht dem Operator '<='. |
__call Metamethode wird aufgerufen, wenn ein Wert in Lua aufgerufen wird. Nachfolgender Beispiel zeigt die Berechnung der Summe der Elemente einer Tabelle:
-- Berechnen Sie den größten Wert im Array, table.maxn in Lua5.2Diese Version kann nicht mehr verwendet werden -- Definieren Sie die benutzerdefinierte Funktion table_maxn, um die Anzahl der Elemente in der Tabelle zu berechnen function table_maxn(t) local mn = 0 for k, v in pairs(t) do if mn < k then mn = k end end return mn end -- Definieren Sie die Metamethode __call mytable = setmetatable({10}, { __call = function(mytable, newtable) sum = 0 for i = 1, table_maxn(mytable) do sum = sum + mytable[i] end for i = 1, table_maxn(newtable) do sum = sum + newtable[i] end return sum end ) newtable = {10,20,30} print(mytable(newtable))
Das Ausgaberesultat des obigen Beispiels ist:
70
Die __tostring-Metamethode wird verwendet, um das Ausgabeverhalten von Tabellen zu ändern. Im folgenden Beispiel haben wir die Ausgabeinhalte der Tabelle angepasst:
mytable = setmetatable({ 10, 20, 30 }, { __tostring = function(mytable) sum = 0 for k, v in pairs(mytable) do sum = sum + v end return "Die Summe aller Elemente im Array beträgt" .. sum end ) print(mytable)
Das Ausgaberesultat des obigen Beispiels ist:
Die Summe aller Elemente im Array beträgt 60
Von diesem Artikel können wir wissen, dass Metatables unsere Code-Funktionen sehr gut vereinfachen können. Daher ist es wichtig, die Metatables von Lua zu verstehen, um einfacher und bessere Lua-Code zu schreiben.