Lua中类的实现
Lua的面向对象
Lua不直接支持面向对象编程,但是可以使用Lua中的表实现类似的功能。
lua
Vector = {
x = 1,
y = 2,
z = 3,
}
function Vector:length()
return math.sqrt((self.x * self.x) + (self.y * self.y) + (self.z * self.z));
end
print(Vector:length())
但是这不是我们想要的实现,我们想要的是类
,而不是对象。
简洁的class实现
我们可以使用Lua中的元表来帮我们实现对象模板,也就是类class概念。
lua
function class(baseClass, body)
local ret = body or {}
if (baseClass ~= nil) then
setmetatable(ret, ret)
ret.__index = baseClass
ret.base = baseClass
end
-- 使用__index元方法创建对象
ret.new = function (self, constructionData, originalSubClass)
local obj
if (self.__index ~= nil) then
if (originalSubClass ~= nil) then
obj = self.__index:new(constructionData, originalSubClass)
else
obj = self.__index:new(constructionData, self)
end
else
obj = constructionData or {}
end
setmetatable(obj, obj)
-- 设置读取对象属性/方法时的查找表,也就是类
obj.__index = self
-- 复制操作运算符
if (self.__operators ~= nil) then
for key, value in pairs(self.__operators) do
obj[key] = value
end
end
return obj
end
ret.isInstance = function (self, otherClass)
local cls = self.__index
while cls do
if cls == otherClass then
return true
end
-- 递归查找
cls = cls.base
end
return false
end
return ret
end
使用方式
lua
------------------------------------------
require("LuaClass")
------------------------------------------
Vec3 = class(nil, {
x = 0,
y = 0,
z = 0
})
function Vec3:length()
return math.sqrt((self.x * self.x) + (self.y * self.y) + (self.z * self.z))
end
vec3 = Vec3:new({x = 1, y = 2, z = 3})
print(vec3:length())
------------------------------------------
Vec4 = class(Vec3, {
w = 4
})
function Vec4:length()
return math.sqrt((self.x * self.x) + (self.y * self.y) + (self.z * self.z) + (self.w * self.w))
end
vec4 = Vec4:new({x = 1, y = 2, z = 3, w = 4})
print(vec4:length())
------------------------------------------
print(vec4:isInstance(Vec3))
Github
https://github.com/TechArtLife/LuaClass
注意:可能有坑!!!
lua
require("LuaClass")
------------------------------------------
Vec3 = class(nil, {
data = {1, 2, 3, x = 0}
})
function Vec3:SetData(value)
self.data.x = value;
end
a = Vec3:new()
b = Vec3:new()
a:SetData(66)
b:SetData(100)
print("a.data.x is :" .. tostring(a.data.x));
print("b.data.x is :" .. tostring(b.data.x));
print("ClassBase.data.x is :" .. tostring(Vec3.data.x));
输出结果
shell
a.data.x is :100
b.data.x is :100
ClassBase.data.x is :100
参考资料
- A simple Class implementation in Lua for Object-Oriented Programming: https://gist.github.com/paulmoore/1429475
- Lua实现Class遇到的一个坑: https://zhuanlan.zhihu.com/p/95306318