lua 是一种脚步语言,语言本身并不具备面向对象的特性。

但是我们依然可以利用语言的特性,模拟出面向对象的特性。

面向对象的特性通常会具备:封装,继承,多态的特性,如何在lua中实现这些特性,最主要的就是利用了lua的table和metatable。

  table是一种强大的关联数组,它可以使用数字和字符串做key,而且可以使用点操作符访问table的元素,因此非常使用用于存储一个对象的属性;

  metatable依然可以认为是一种关联数组,但是元表的作用更加强大,主要是:

    1.定义算术操作符和关系操作符的行为
    2.为 Lua 函数库提供支持
    3.控制对 table 的访问

  利用这个特性,我们可以把某个对象的方法存在元表中,当访问对象的方法时,如果自身不具备这个方法,就会在元方法中去寻找,因此利用元表可以轻松实现继承和多态的特性;

关于lua的具体实现:

-- 检查类名是否合法,要求是字符串
function validateClassName(className)
local _type = type(className); if (_type == "string") then
local _len = string.len(className) if (_len <= ) then
return true
else
print("[error] class name length is greater than 40")
return false
end
else
print("[error] class name of class is not a string")
return false
end
end -- 检查属性表是否合法,属性只允许是基本类型(包括number,boolean,string,table,nil)
function validatePropTabel(propTable)
for _, _v in pairs(propTable) do
local _propType = type(_v); if (_propType == "number" or
_propType == "boolean" or
_propType == "string" or
_propType == "table" or
_propType == "nil") then
return true
else
print("[error] prop of class only support base type(number, boolean, string, table, nil), current type is ".._propType)
return false
end
end
end -- 检查父类是否合法,父类目前只支持table类型
function validateSuperClass(superClass)
local _superType = type(superClass) if (_superType == "table" or
_superType == "nil") then
return true
else
print("[error] super class is not a table")
return false
end
end -- className: 创建新类的类名
-- propTable: 新类的属性
-- superClass: 父类
function class(className, propTable, superClass)
print("------------------------------------------------------")
print("[info] create new class <"..className..">:") -- 验证参数合法性
if (not validateClassName(className) or
not validatePropTabel(propTable) or
not validateSuperClass(superClass)) then
return nil
else
print("[info] arguments validated")
end -- 创建新类
local subClass = {}
-- 设置类名
subClass.__className = className
-- 设置元方法
subClass.__index = subClass
-- 设置属性表
subClass.props = propTable
-- 设置父类
if (superClass) then
setmetatable(subClass, superClass)
subClass.super = superClass print("[info] extended from super class "..superClass.__className)
else
subClass.super = nil print("[info] super class is nil")
end -- 设置默认构造函数
if (not subClass.ctor) then
subClass.ctor = function(...)
print(className.." default construct...")
end print("[info] add default constructor")
end
-- 设置默认的析构函数
if (not subClass.dtor) then
subClass.dtor = function()
print(className.." default destruct...")
end print("[info] add default destructor")
end -- 设置new方法
subClass.new = function(...)
-- 创建一个新的实例
local instance = {} -- 继承父类默认的属性
local _cls = subClass.super
while (_cls) do
if (_cls.props) then
print("------------------------------------------------------")
print("[info] extended prop from super class <".._cls.__className..">:")
for _k, _v in pairs(_cls.props) do
print("[info] ".._cls.__className.." key:"..tostring(_k).." value:"..tostring(_v))
instance[_k] = _v
end
print("------------------------------------------------------")
end
_cls = _cls.super
end
-- 设置本类的属性
if (propTable) then
print("------------------------------------------------------")
print("[info] extended prop from super class <"..className..">:")
for _k, _v in pairs(propTable) do
print("[info] "..className.." key:"..tostring(_k).." value:"..tostring(_v))
instance[_k] = _v
end
print("------------------------------------------------------")
end -- 设置实例的元表为本类
setmetatable(instance, subClass)
-- 调用实例的构造函数
instance:ctor(...) print("[info] create instance of class <"..className..">") return instance
end
-- 设置delete方法
subClass.delete = function(instance)
-- 调用实例的析构函数
instance:dtor() -- 删除实例的数据
print("------------------------------------------------------")
print("[info] delete prop from super class <"..className..">:")
for _k, _v in pairs(instance) do
print("[info] "..className.." key:"..tostring(_k).." value:"..tostring(_v))
instance[_k] = nil
end
print("------------------------------------------------------")
-- 删除实例的元表
setmetatable(instance, nil)
-- 删除实例
instance = nil print("[info] delete instance of class <"..className..">")
end print("------------------------------------------------------") return subClass
end

lua 中的面向对象的更多相关文章

  1. Cocos2d-x 脚本语言Lua中的面向对象

    Cocos2d-x 脚本语言Lua中的面向对象 面向对象不是针对某一门语言,而是一种思想.在面向过程的语言也能够使用面向对象的思想来进行编程. 在Lua中,并没有面向对象的概念存在,没有类的定义和子类 ...

  2. lua中的面向对象编程

    简单说说Lua中的面向对象 Lua中的table就是一种对象,看以下一段简单的代码: 上述代码会输出tb1 ~= tb2.说明两个具有相同值得对象是两个不同的对象,同时在Lua中table是引用类型的 ...

  3. Lua和C++交互 学习记录之九:在Lua中以面向对象的方式使用C++注册的类

    主要内容转载自:子龙山人博客(强烈建议去子龙山人博客完全学习一遍) 部分内容查阅自:<Lua 5.3  参考手册>中文版 译者 云风 制作 Kavcc vs2013+lua-5.3.3 在 ...

  4. 【转载】【游戏开发】在Lua中实现面向对象特性——模拟类、继承、多态

    [游戏开发]在Lua中实现面向对象特性——模拟类.继承.多态   阅读目录 一.简介 二.前提知识 三.Lua中实现类.继承.多态 四.总结 回到顶部 一.简介 Lua是一门非常强大.非常灵活的脚本语 ...

  5. Lua中的面向对象编程详解

    简单说说Lua中的面向对象 Lua中的table就是一种对象,看以下一段简单的代码: 复制代码代码如下: local tb1 = {a = 1, b = 2}local tb2 = {a = 1, b ...

  6. 【游戏开发】在Lua中实现面向对象特性——模拟类、继承、多态

    一.简介 Lua是一门非常强大.非常灵活的脚本语言,自它从发明以来,无数的游戏使用了Lua作为开发语言.但是作为一款脚本语言,Lua也有着自己的不足,那就是它本身并没有提供面向对象的特性,而游戏开发是 ...

  7. Lua 中使用面向对象(续)

    上一篇文章给了一个面向对象的方案,美中不足的是没有析构函数 Destructor,那么这一次就给它加上. 既然是析构,那么就是在对象被销毁之前做该做的事情,lua 5.1 的 userdata 可以给 ...

  8. Lua中的userdata

    [话从这里说起] 在我发表<Lua中的类型与值>这篇文章时,就有读者给我留言了,说:你应该好好总结一下Lua中的function和userdata类型.现在是时候总结了.对于functio ...

  9. 9----Lua中的面向对象

    什么是面向对象? 使用对象.类.继承.封装.消息等基本概念来进行程序设计 面向对象最重要的两个概念就是:对象和类 对象是系统中用来描述客观事物的一个实体,它是构成系统的一个基本单位 一个对象由一组属性 ...

随机推荐

  1. 关于jquery中的事件绑定bind()和live()

    live可以说是bind是方法的变种. 二者的主要区别就是live方法的作用机理是事件委托,live方法的作用机理是将事件绑定DOM的根节点上. live方法的处理机制就是把事件绑定在DOM树的根节点 ...

  2. Windows 2012 装 Remote Desktop Organizer 无法连接到其他远程服务器

    一句话,版本太低 换Remote Desktop Organizer 1.4.5版本就ok 了

  3. readfile() 函数

    定义和用法 readfile() 函数输出一个文件. 该函数读入一个文件并写入到输出缓冲. 若成功,则返回从文件中读入的字节数.若失败,则返回 false.您可以通过 @readfile() 形式调用 ...

  4. CentOS 7 为firewalld添加开放端口及相关资料

    1.运行.停止.禁用firewalld 启动:# systemctl start  firewalld 查看状态:# systemctl status firewalld 或者 firewall-cm ...

  5. 腾讯优测干货精选|Android双卡双待适配——隐藏在数据库中的那些秘密

    腾讯优测是专业的app自动化测试平台,除了提供兼容性测试,远程真机租用等多维度的测试服务,还有优分享-腾讯内部的移动研发测试干货精选~ 许多APP都希望获取用户通讯录联系人,利用通讯录关系链信息来丰富 ...

  6. 防止特殊html字符的问题(xxs攻击)方法

    快速对字符转义,避免跨站攻击XSS   XSS已经成为非常流行的网站攻击方式,为了安全起见,尽量避免用户的输入.可是有些情况下不仅不避免,反而要求鼓励输入,比如写博客.博客园开放性很高,可以运行手写的 ...

  7. Sprint第二个冲刺(第十天)

    一.Sprint 计划会议: 现在总结一下情况,正在做的3个功能的完成程度已经达到了80%,过几天就可以完成了.也把之前做的修改界面放入fragment中,方便修改管理.效果图如下: 二.Sprint ...

  8. Cookie初识篇

    一.什么是Cookie Cookie,有时也用其复数形式Cookies,指某些网站为了辨别用户身份.进行session跟踪而储存在用户本地终端上的数据(通常经过加密).定义于RFC2109和2965都 ...

  9. HTML 空格的表示符号 nbsp / ensp / emsp 的区别

    HTML 空格的表示符号 nbsp / ensp / emsp 的区别?     半角的不断行的空白格(推荐使用)    半角的空格    全角的空格

  10. 用JS编写日历的简单思路

    提要:本文以写当前时间环境下当月的日历表为例,用最简单的方法实现JavaScript日历,旨在展示JS世界中实用为本.简单为上的解决问题的思路. Web页中的日历一般离不开表格,通常都使用表格装载指定 ...