本文共 2938 字,大约阅读时间需要 9 分钟。
1: Lua 提供了元表(Metatable),允许我们改变table的行为,每个行为关联了对应的元方法。
例如,使用元表我们可以定义Lua如何计算两个table的相加操作a+b。
当Lua试图对两个表进行相加时,先检查两者之一是否有元表,之后检查是否有一个叫"__add"的字段,若找到,则调用对应的值。"__add"等即时字段,其对应的值(往往是一个函数或是table)就是"元方法"。
语法:
mytable = {"lua","C#","C++"} --普通表myMetatable = {} --元表 元表扩展了普通表的行为mytable = setmetatable(mytable,myMetatable) --用来设置元表print(getmetatable(mytable))
2: 元方法的使用; 元方法是用来定义元表的行为
__index
1:第一种情况后接对应的方法:
mytable = {"lua","C#","C++"} --普通表--元表 元表扩展了普通表的行为myMetatable = { __index = function(tab,key) print("调用了元表中的方法") -- body end} mytable = setmetatable(mytable,myMetatable) --用来设置元表--当访问普通表中的下标值时,可以访问的到,那么就返回对应值print(mytable[1])--当访问普通表中的下标值不存在时,这个时候就会去调用元方法,tab就是对应的普通表,key就是对应的下标值print(mytable[10])
2:第二种情况接对应的表:
mytable = {"lua","C#","C++"} --普通表myNewTable = {}myNewTable[8] = "C"myNewTable[9] = "PHP"myNewTable[10] = "Python"--元表 元表扩展了普通表的行为myMetatable ={__index = myNewTable} mytable = setmetatable(mytable,myMetatable) --用来设置元表--当访问普通表中的下标值时,可以访问的到,那么就返回对应值print(mytable[1])--当访问普通表中的下标值不存在时,这个时候就会去调用元方法,tab就是对应的普通表,key就是对应的下标值print(mytable[10]) --Python
__newindex
1:对应方法
--__newindex当我们对表的数据进行修改的时候,修改的是一个新的索引才会起作用--当我们给表添加新的键值对的时候才会使用__newindexmytable = {"lua","C#","C++"} --普通表myMetatable = { __newindex = function(tab,key,value) print("我们要修改的key为"..key.."把这个key值修改为:"..value) rawset(tab,key,value) -- body end}mytable = setmetatable(mytable,myMetatable)mytable[1] = "C#"mytable[5] = "Lua"print(mytable[5])
3:为元表添加操作符
mytable = {"lua","java","C#","C++"}myMetatable = { __add = function(tab,tab1) -- body print("调用加法操作符") local maxindex = 0 maxindex = #tab for k,v in pairs(tab1) do maxindex = maxindex + 1 table.insert(tab,maxindex,v) end end}mytable = setmetatable(mytable,myMetatable)newtable = {"PHP","Python"}c = mytable+newtable --必须要有接收表for k,v in pairs(mytable) do print(k,v)end
__add 键包含在元表中,并进行相加操作。 表中对应的操作列表如下:(注意:__是两个下划线)
模式 | 描述 |
---|---|
__add | 对应的运算符 '+'. |
__sub | 对应的运算符 '-'. |
__mul | 对应的运算符 '*'. |
__div | 对应的运算符 '/'. |
__mod | 对应的运算符 '%'. |
__unm | 对应的运算符 '-'. |
__concat | 对应的运算符 '..'. |
__eq | 对应的运算符 '=='. |
__lt | 对应的运算符 '<'. |
__le | 对应的运算符 '<='. |
4:__call方法调用。调用值时调用
--__call 元方法在 Lua 调用一个值时调用mytable = {"lua","java","C#"}myMetatable = { __call = function(tab,arg,arg2,arg3,arg4) -- body print("调用了Call方法",arg,arg2,arg3,arg4) return "xxz" end}mytable = setmetatable(mytable,myMetatable)v = mytable(1,2,3)print(v)
5:__tostring方法调用。_tostring 元方法用于修改表的输出行为。
--__call 元方法在 Lua 调用一个值时调用mytable = {"lua","java","C#"}myMetatable = { __call = function(tab,arg,arg2,arg3,arg4) -- body print("调用了Call方法",arg,arg2,arg3,arg4) return "xxz" end, --__tostring 元方法在修改表的输出行为 __tostring = function(tab) -- body a = "" for k,v in pairs(tab) do a = a ..v.."," end return a end}mytable = setmetatable(mytable,myMetatable)v = mytable(1,2,3)print(v)print(mytable)
转载地址:http://sbemn.baihongyu.com/