0.简单前言
1、面向对象主要四个特征:封装,继承,多态,抽象
2、Lua是种简单精致小巧的语言,其本质是个表(table),变量和方法皆可看作为该表的元素。
P.S. 该博客和代码为个人编写习惯以及为后续博客内容拓展服务考虑,若有错误等不周到的地方还请包涵以及指出。
1.类
尽管可能不太完美,但我们依旧可以通过元表的方式实现类以及类的继承。
lua
-- 元类
local Rectangle = {area = 0, length = 0, breadth = 0}
-- 派生类的方法 new
function Rectangle:new (o,length,breadth)
local o = o or {}
setmetatable(o, self) -- 将Rectangle赋值给要返回的对象作为元表
self.__index = self -- 通过 .__index 传递元表元素
self.length = length or 0
self.breadth = breadth or 0
self.area = length*breadth;
return o
end
-- 派生类的方法 printArea
function Square:printArea ()
print("矩形面积为 ",self.area)
end
简单结构就是这样,Square类已经继承Rectangle的属性以及方法,同时还拓展出自己的新方法 printArea(),但实际运用起来并不方便。
2.改进
class类
用于构建模板以及进行类的继承
Class.lua
lua
-- params:要实例的类,继承
function class(classname , ...)
local cls = {}
local supers = {...}
for _ , super in ipairs(supers) do
local superType = type(super)
if superType == "function" then
cls.__create = super
elseif superType == "table" then
cls.__supers = cls.__supers or {}
cls.__supers[#cls.__supers + 1] = super
end
end
cls.__index = cls
cls.__class = classname
if not cls.__supers then
-- 没有继承其他类
-- 添加默认构造函数
-- __index指向自己不变
cls.Ctor = function() end
elseif #cls.__supers == 1 then
-- 单继承的情况
local super = cls.__supers[1]
cls = setmetatable(cls , {__index = super})
cls.super = super -- 模拟super关键字
else
-- 多继承的情况
-- 使index指向一个函数,在索引时遍历父类
cls = setmetatable(cls , {__index = function(_ , key)
for _ , super in ipairs(cls.__supers) do
if super[key] then
return super[key]
end
end
end})
end
cls.New = function(...)
-- 前面只是将几个类进行合并,因此在实例时还需进行一次元表
local instance = setmetatable({}, cls)
instance.class = cls
instance:Ctor(...)
return instance
end
-- 返回实例
return cls
end
实验
创建4个脚本A,B,C,D。
使得C继承A,
D继承A,B。
A.lua
lua
A = class(A)
function A:Ctor()
print("We create a class A!")
end
function A:Fun_A()
print("This is a function from class A!")
end
return A
B.lua
lua
B = class(B)
function B:Ctor()
print("We create a class B!")
end
function B:Fun_B()
print("This is a function from class B!")
end
return B
C.lua
lua
C = class(C , A) -- 让C类单独继承A类
function C:Ctor()
print("We create a class C!")
end
function C:Fun_C()
print("This is a function from class C!")
end
return C
D.lua
lua
D = class(D , A , B) -- 让D类同时继承A,B类
function D:Ctor()
print("We create a class D!")
end
function D:Fun_D()
print("This is a function from class D!")
end
return D
检验
main.lua
lua
-- 实例以及覆写方法
local test_c = C:New()
local test_d = D:New()
-- 子类自身的方法
test_c:Fun_C()
test_d:Fun_D()
-- 子类继承的方法
test_c:Fun_A()
test_d:Fun_A()
test_d:Fun_B()
-- 没有继承的方法
-- test_c:Fun_B()
结果
lua
We create a class C!
We create a class D!
This is a function from class C!
This is a function from class D!
This is a function from class A!
This is a function from class A!
This is a function from class B!
若把注释取消,则直接报attempt to call a nil value (method 'Fun_B')