昨天本来还想写一篇love2d之角色移动的,可是不知怎么回事,
我在一个类里有setXY(),在love.load()里调用了,可是居然没
按我的预想坐标,而是直接显示在了顶点.后来各种print,发现
确实是调用了,但就是不显示,郁闷,只好作罢.
后来也想不出原因,于是又看了一下lua面向对象,想到以后可能
很多地方会用到类,便想找一个简洁的lua面向对象的扩展.先推荐一个很好的lua博客,当lua语法不懂时,我常去翻阅.
到http://lua-users.org翻了一下,发现了一些面向对象的扩展,最终选择
了middleclass.middle意为中等,表明其是中等规模的
面向对象实现(作者介绍的),官网为[https://github.com/kikito/middleclass/](https://github.com/kikito/middleclass/()
不到140行代码就实现了,类,继承,虚函数,私有变量等.(下面的示例已带middleclass,可以不用下载)
作者也提到了没有实现的有
- metaclasses 元类吗?不知道
- classes are not Objects (instances are) 类的实例是Objects,而类不是
- simulating a ‘super’ keyword (for performance concerns) 因为效率,没有模拟'super'关键字
根据作者的提示,简单的看看middleclass源码,发现在下面摘录的片断里第4步才setmetatable(),即在class的实例new()之后,
才把其绑定到Object上.(只是简单的看了一下,不确定正否,希望漂过的高手指正)
--1步function class(name, super, ...)
super = super or Object
return super:subclass(name, ...)
end--2步function Object.static:subclass(name) assert(_classes[self], "Make sure that you are using 'Class:subclass' instead of 'Class.subclass'") assert(type(name) == "string", "You must provide a name(string) for your class") local subclass = _createClass(name, self) _setClassMetamethods(subclass) _setDefaultInitializeMethod(subclass, self) self.subclasses[subclass] = true self:subclassed(subclass) return subclassend--3步function Object.static:new(...) local instance = self:allocate() instance:initialize(...) return instanceend--4步function Object.static:allocate() assert(_classes[self], "Make sure that you are using 'Class:allocate' instead of 'Class.allocate'") return setmetatable({ class = self }, self.__instanceDict)end
下面我们来使用middleclass,看其带来的方便之处(以下的内容来自官方文档,
英语好的同学可以自己去看).只介绍类和继承,其它的功能现在还用不上,等以后
再说.
test.lua
require 'middleclass'
--声明一个类,也可用class('Person', Object) 或Object:subclass('Person') middleclass的根类是Object
Person = class('Person')
--构造函数
function Person:initialize(name)
self.name = name
end
function Person:speak()
print('Hi, I am ' .. self.name ..'.')
end
--继承或Person:subclass('AgedPerson')
AgedPerson = class('AgedPerson', Person)
--类变量
AgedPerson.static.ADULT_AGE = 18
--注意在子类里要调用父类里的构造函数
function AgedPerson:initialize(name, age)
Person.initialize(self, name) --注意在子类里要调用父类里的构造函数
self.age = age
end
--覆盖子类里的方法,感觉确实像从c++里的虚函数
function AgedPerson:speak()
Person.speak(self)
--可以实例里直接访问类变量
if(self.age < AgedPerson.ADULT_AGE) then
print('I am a child.')
else
print('I am an adult.')
end
end
--等价于AgedPerson('Billy the Kid', 13),new()隐含调用
local p1 = AgedPerson:new('Billy', 13)
local p2 = AgedPerson:new('Luke', 21)
p1:speak()
print("----------------")
p2:speak()
代码,已clone的直接git pull
git clone git://gitcafe.com/dwdcth/love2d-tutor.git
或git clone https://github.com/dwdcth/mylove2d-tutor-in-chinese.git
原文链接: https://www.cnblogs.com/xdao/archive/2012/12/27/lua-middleclass-intro.html
欢迎关注
微信关注下方公众号,第一时间获取干货硬货;公众号内回复【pdf】免费获取数百本计算机经典书籍
原创文章受到原创版权保护。转载请注明出处:https://www.ccppcoding.com/archives/73807
非原创文章文中已经注明原地址,如有侵权,联系删除
关注公众号【高性能架构探索】,第一时间获取最新文章
转载文章受原作者版权保护。转载请注明原作者出处!