Metatable元方法讲解

转载自:http://www.cnblogs.com/JimLy-BUG/p/5364281.html

 

一、 __index元方法

__index元方法:用于查看表中元素是否存在,如果不存在返回结果为nil;如果存在,则由__index返回结果

  存在__index元方法:

复制代码
myTable = setmetatable({key1 = "lua", key3 = "java"}, {
    __index = function(myTable, key)
        if key == "key2" then
          return "key2 is nil"
      else
          return myTable[key]
      end
    end
})
复制代码

  程序运行输出:

---------- 新建程序 ----------
lua    key2 is nil    java

输出完成 (耗时 0 秒) - 正常终止

 

  不存在__index元方法:

myTable = {key1 = "lua", key3 = "java"}

print(myTable.key1, myTable.key2, myTable.key3)

  程序运行输出:

---------- 新建程序 ----------
lua    nil    java

输出完成 (耗时 0 秒) - 正常终止

 

二、__newindex元方法

__newindex元方法:用来对表进行更新。给一个表的缺少的索引赋值时,解释器就会查找是否存在__newindex元方法,

          如果存在则调用这个函数而不进行赋值操作;不存在则进行赋值操作。(只针对表中不存在的索引有效)

  存在__newindex元方法:

复制代码
myTable = {key1 = "lua", key3 = "java"}

setmetatable(myTable, {
    __newindex = function(myTable, key, value)
      print(key .. " is not exists in myTable " .. value)
    end
})

myTable.key1 = "hello"
myTable.key2 = "world"    --给key2赋值会执行__newindex函数

print(myTable.key1, myTable.key2)
复制代码

  程序运行输出:

---------- 新建程序 ----------
key2 is not exists in myTable world
hello    nil

输出完成 (耗时 0 秒) - 正常终止

  解释说明:  在给myTable表的key1索引赋值时,因为key1索引是myTable中已经存在的索引,

       所以只进行赋值而不调用__newindex元方法;

         在给myTable表的key2索引赋值时,因为key2索引在myTable表中不存在,解释器就会查找

       是否存在__newindex元方法,又由于存在__newindex元方法,所以调用了__newindex元方法

       而不对key2索引进行赋值;若不存在__newindex方法,则对新索引进行赋值操作。 

 

   不存在__newindex元方法:

复制代码
myTable = {key1 = "lua", key3 = "java"}

myTable.key1 = "hello"
myTable.key2 = "world"    

print(myTable.key1, myTable.key2)
复制代码

  程序运行输出:

---------- 新建程序 ----------
hello    world

输出完成 (耗时 0 秒) - 正常终止

 

三、__add元方法

 __add元方法:用于操作表与表之间的关联事件。当两张表之间用到字符'+'时,解释器就会去查找是否存在__add元方法,

        若存在__add元方法,则调用__add元方法,否则程序执行报错。(对应的运算符:'+')

   存在__add元方法:

复制代码
myTable = {10, 20, 30}
newTable = {20, 30, 40}

setmetatable(myTable, {
    __add = function(myTable, newTable)
      print("add")    --此处用来处理相关事件,可遍历两个对其中的元素进行累加求和并返回
      return "already add"
    end
})

print(myTable + newTable)
复制代码

  程序运行输出:

---------- 新建程序 ----------
add
already add

输出完成 (耗时 0 秒) - 正常终止

 

四、__sub元方法

 __sub元方法:用法类似于__add元方法。(对应的运算符:'-')

复制代码
myTable = {10, 20, 30}
newTable = {20, 30, 40}

setmetatable(myTable, {  
    __sub = function(myTable, newTable)  --__sub可替换__mul/__div/__mod/__unm/__concat/__eq/__lt/__le
      print("subtract")    --处理相关事件
      return "already subtract"
    end
})

print(myTable - newTable)  --此处要替换为相应的对应运算符
复制代码

  程序运行输出:

---------- 新建程序 ----------
subtract
already subtract

输出完成 (耗时 0 秒) - 正常终止

 类似于__add和__sub元方法的还有:

  __mul元方法:对应运算符'*'

  __div元方法:对应运算符'/'

  __mod元方法:对应运算符'%'

  __pow元方法:对应运算符'^'

  __unm元方法:对应运算符'-',此处的运算符不是减号,是代表负数

  __concat元方法:对应运算符'..'

  __eq元方法:对应运算符'=='

  __lt元方法:对应运算符'<'

  __le元方法:对应运算符'<='

 

最后再拿__unm元方法举例:

复制代码
myTable = {10, 20, 30}

setmetatable(myTable, {
    __unm = function(myTable)
      print("nagative")    --处理相关事件
      return "already nagative"
    end
})

print(-myTable)
复制代码

  程序运行输出:

---------- 新建程序 ----------
nagative
already nagative

输出完成 (耗时 0 秒) - 正常终止

 

五、__call元方法

 __call元方法:用于表变量调用一个参数时调用__call元方法。

复制代码
myTable = {10, 20, 30}
num = 100

setmetatable(myTable, {
    __call = function(myTable, param)    --此处的param可替换其他类型的变量
      print("call " .. param)    --处理相关事件
      return "already call"
    end
})

print(myTable(num))  --myTable调用num变量
复制代码

  程序运行输出:

---------- 新建程序 ----------
call 100
already call

输出完成 (耗时 0 秒) - 正常终止

 

六、__tostring元方法

 __tostring元方法:用于修改表的输出行为。【类似于JAVA中类中重写了toString()方法,用于修改对象的输出行为

复制代码
--写法一
myTable = {10, 20, 30}

setmetatable(myTable, {
    __tostring = function(myTable)    --注意__tostring是两个_开头
      local sum = 0
      for _,v in pairs(myTable) do  --注意此处的_字符也表示变量,可用字母k或其他字母替代
          sum = sum + v
      end
      return ("表元素之和=" .. sum)
    end
})

print(myTable)


--写法二 myTable = {10, 20, 30} mt = {} mt.__tostring = function(myTable) local sum = 0 for _,v in pairs(myTable) do   sum = sum + v end return ("表元素之和=" .. sum) end setmetatable(myTable, mt) print(myTable)
复制代码

  循环遍历部分也可修改为:

for index = 1,#myTable do
    sum = sum + myTable[index]
end

  程序运行输出:

---------- 新建程序 ----------
表元素之和=60

输出完成 (耗时 0 秒) - 正常终止

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值