元表(metatable)是 Lua 里每種類型的值的默認操作方式的集合,例如,數(shù)字可以加減乘除、字符串可以連接合并、table 可以插入一對 key-value 值、函數(shù)可以被調(diào)用等等,這些操作都遵循其預定義的行為來執(zhí)行。
而值的默認操作方式不是一成不變的,可以通過元表來修改其行為表現(xiàn),或者是新定義一些默認沒有的操作。例如,當兩個 table 相加時, Lua 會檢查它們之間的元表里是否有 "__add" 這個函數(shù),如果定義有這個函數(shù), 則調(diào)用這個函數(shù)來執(zhí)行一次加法操作。
這里,相加這個操作的函數(shù)名 -- "__add" 是元表的鍵名(元表的鍵名也稱之為事件(event),一般以 2 個下劃線 "_" 開頭),而 "__add" 函數(shù)則是這個相加操作的元方法(metamethod)。對于值的操作,Lua 都將其關聯(lián)上一個被稱作事件的指定健,當 Lua 需要對一個值發(fā)起這些操作中的一個時, 它會去檢查值的元表里是否有對應事件。如果有,則鍵名對應的值(元方法)將控制 Lua 怎樣去執(zhí)行這個操作。
getmetatable - 獲取元表
Lua 里每個值都有一個元表。table 類型和 userdata 類型的值可以有各自獨立的元表,而其他類型的值則是公用其類型所預先定義的元表。例如,可以用 getmetatable 來獲取一個字符串的元表:
復制代碼 代碼如下:
a = "just a test"
print(getmetatable(a))
上面的操作會輸出 "table: 0x7fa8614080f0" 的 table,里面包含著預先定義給字符串的操作方法,其內(nèi)容結構如下:
復制代碼 代碼如下:
-__index-sub [function: 0x7fee39408050]
-upper [function: 0x7fee394080a0]
-len [function: 0x7fee39407ec0]
-gfind [function: 0x7fee39407e20]
-rep [function: 0x7fee39407fb0]
-find [function: 0x7fee39407d30]
-match [function: 0x7fee39407f60]
-char [function: 0x7fee39407c90]
-dump [function: 0x7fee39407ce0]
-gmatch [function: 0x7fee39407e20]
-reverse [function: 0x7fee39408000]
-byte [function: 0x7fee39407c40]
-format [function: 0x7fee39407d80]
-gsub [function: 0x7fee39407e70]
-lower [function: 0x7fee39407f10]
Lua 在創(chuàng)建新的 table 時不會創(chuàng)建元表,因此想調(diào)用 getmetatable 函數(shù)獲取其元表的話,只會返回一個 nil 值。
復制代碼 代碼如下:
tbl = {}
print(getmetatable(tbl))
setmetatable - 修改元表
對于上面所說的新創(chuàng)建的 table 是空元表的問題,可以用 setmetatable 來修改其元表:
復制代碼 代碼如下:
tbl = {}
t1 = {key = "val"}
setmetatable(tbl, t1)
print(getmetatable(tbl))
對于上面所說的 2 個 table 相加的情況,可以給 table 添加一個 __add 的元方法就可以進行相加操作:
復制代碼 代碼如下:
t1 = {"a", "b", "c", "d"}
t2 = {5, 6, 7, 8, 9}
mt = {}
mt.__add = function(a, b)
local tbl = {}
local ret = {}
for k, v in pairs(a) do tbl[v] = true end
for k, v in pairs(b) do tbl[v] = true end
for k, v in pairs(tbl) do
table.insert(ret, k)
end
return ret
end
setmetatable(t1, mt)
setmetatable(t2, mt)
t = t1 + t2
for k, v in pairs(t) do print(v) end
您可能感興趣的文章:- Lua學習筆記之數(shù)據(jù)類型
- Lua學習筆記之運算符和表達式
- Lua學習筆記之表和函數(shù)
- Lua學習筆記之數(shù)據(jù)結構
- Lua基礎教程之表(Table)學習筆記
- Lua基礎教程之賦值語句、表達式、流程控制、函數(shù)學習筆記
- Lua入門學習筆記
- Lua字符串庫(string庫)學習筆記
- Lua模塊與包學習筆記
- Lua面向?qū)ο缶幊虒W習筆記
- Lua中的閉包學習筆記
- Lua中的table學習筆記
- Lua 學習筆記之C API 遍歷 Table實現(xiàn)代碼
- Lua表達式和控制結構學習筆記
- Lua學習筆記之類型與值