lua模拟类

介绍两种,一种是通过设置元表,一种通过拷贝table

Shape = {perimeter = 0 , area = 0} ---相当于类,perimeter和area相当于属性

Shape.__index = Shape   ----设置元方法指向自身

function Shape:New()  ---- 创建对象的方法,这里类实例化类似于新建了table,这个table的元表示shape类
	local temTab = {}   -----新建设一个table
	setmetatable(temTab,Shape)  ----设置table的元表为shape,
	--[[lua中table的查找顺序是先在自己table中找,如果没有就看有没有元表,如果没有元表,则直接返回nil,如果有元表判断元表是否设置了元方法,上面的__index就是这时候使用,__index方法是一张表,则重复执行,如果__index方法是一个函数,则返回该函数的返回值]]
	temTab.perimeter = 3
	temTab.area = 2
	return temTab
end

function Shape:GetArae()
    return self.area
end 

function Shape:GetPerimeter()
    return self.perimeter
end  

Rectangle = {}
setmetatable(Rectangle, Shape)  --Rectangle 通过设置原表继承自shape类
Rectangle.__index = Rectangle  
function Rectangle:New(width,height)  
    local t = {}             --初始化对象自身        
    setmetatable(t, Rectangle)   --将对象自身元表设定为SubClass类  
    t.width = width 
    t.height = height        --新的属性初始化,如果没有将会按照声明=0  
    return t  
end  

function Rectangle:GetArae()
	local rectangleArea = self.width*self.height
    return rectangleArea
end 

acc = Shape:New()
print("acc.GetArae()  "..acc:GetArae())
print("acc.GetPerimeter  "..acc:GetPerimeter())


tangle = Rectangle:New(5,5)
print(" tangle.width  "..tangle.width.." tangle.height  "..tangle.height)
print("tangle.GetArae()  "..tangle:GetArae())
print("tangle.GetPerimeter  "..tangle:GetPerimeter())

Shape = {perimeter = 2 , area = 2} ---相当于类,perimeter和area相当于属性

Shape.__index = Shape   ----设置元方法指向自身

function Shape:ctor()
	print("base.ctor")
end

function Shape:New()  ---- 创建对象的方法
end

function Shape:GetArae()
    return self.area
end 

function Shape:GetPerimeter()
    return self.perimeter
end  

function Shape:DefineSubClass()--通过拷贝的方式实现模拟类
    local newClassTable = {}

	for k,v in pairs(self) do --拷贝父类shape所有的属性
		newClassTable[k] = v
	end

	newClassTable.base = self --子类的base设为父类
	newClassTable.__index = newClassTable --元方法__index更新索引指向自己

	local NewFunc = function(...)
		local instance = setmetatable({}, newClassTable) --模拟实例化
		instance:ctor(...)  --调用子类的属性
		return instance
	end
	if self.New then
		newClassTable.New = NewFunc --给new赋值方法NewFunc
	end
	return newClassTable
end  


Rectangle = Shape:DefineSubClass() --定义子类

function Rectangle:ctor() --属性,我们可以通过rawget函数来忽略元表的__index作用,只从table中查找
	print("ctor")
	self.base.ctor(self)
	rawset(self, "width", 5)
	rawset(self, "height", 5)
end

function Rectangle:GetArae()
	local rectangleArea = self.width*self.height
    return rectangleArea
end 
print("------------------")
tangle = Rectangle:New()
print("tangle.width  "..tangle.width.." tangle.height  "..tangle.height)
print("tangle.GetArae()  "..tangle:GetArae())
print("tangle.GetPerimeter  "..tangle:GetPerimeter())

 小伙伴们觉得那种方法比较好呢,欢迎讨论

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值