课时 11 · 元表与元方法

课时 11 · 元表与元方法(Lua 进阶):理解元表机制并用于扩展表。含可运行的示例代码、练习与验收要点,示例锁定 Lua 5.1,可在站内在线运行验证。

教程/第二部分 · Lua 进阶更新于 2026-10-073 个小节 教程第 14 / 23 篇 Lua进阶

本课的代码可以就地复制;点代码块右上角的「运行这段」, 会带着这段代码打开 Lua 在线运行器 并直接跑出结果 (课程示例统一按 5.1 跑;运行器里也能切到 5.3)。

本课的代码跑在 996 引擎里,用到的是服务端接口(changeexp、 SetInt 这类),在线运行器里没有这些函数。 每个函数的签名都能在 文档检索 里按名字查到原文。

本课目标

  • 理解元表机制并用于扩展表。

知识讲解

元表(metatable)是普通表,通过 setmetatable 挂到另一张表上,控制后者的行为。常用元方法:__index(访问不存在键时回调,可实现继承与默认值)、__newindex(给不存在键赋值时回调,可实现只读表)、__add/__sub 等(运算符重载)、__tostring(print 时的表现)、__call(把表当函数调用)。rawget/rawset 绕过元方法直接读写。

示例:元表基础

local defaults = { hp = 100 }
local obj = setmetatable({}, { __index = defaults })
print(obj.hp)             -- 100(继承默认值)

local ro = {}
setmetatable(ro, {
    __newindex = function() error('只读表,禁止写入') end
})
local ok, err = pcall(function() ro.x = 1 end)
print('写入被拒绝:', err)   -- 只读表生效

练习任务

  • 实现只读表与带默认值的表:只读表写入时报错;默认值表读取缺省键时返回预设值,读取已有键返回原值。

参考:只读表与默认值表

function readonly(t)
    return setmetatable({}, {
        __index = t,
        __newindex = function() error('attempt to write readonly table') end,
    })
end

function with_default(default)
    return setmetatable({}, { __index = function(_, k) return default[k] end })
end
local cfg = with_default({ gold = 1000 })
print(cfg.gold, cfg.notexist)   -- 1000  nil(default 中无此键)
本篇依据
  • 《996 新三端 Lua 开发教学技术手册》课时 11

参数与取值以你本机版本的官方帮助文档为准,不同版本之间有过调整。