Lua-简单的聊一下闭包,并使用闭包创建一个简单的安全沙盒

概念

1.lua中的闭包(closure)由一个函数,以及函数会用到的变量(upvalue)组成。
2.变量没有说是全局或者局部,因为这里的变量既不是全局,也不是局部的。
3.闭包的使用更像是创建了一个临时的环境,这个临时环境中,变量可供这个环境内所有函数调用,但是离开这个闭包环境,这些变量是不可访问的。

用处

1.闭包可以利用内嵌的私有函数,很巧妙的实现一些简单的面向对象的的逻辑,比如我们要判断一个生成一个圆的判断对象,
传统做法:

function in_circle(x,y,r,check_x,check_y) 
	return (check_x -x)^2 + (check_y-y)^2 <=r^2;
end

这样写是可以的,但是如果持续判断一连串的点是否在同一个圆内的时候就显得很累赘,并且要求的参数过于多,理解起来也相对麻烦,如果是面向对象的写法可以写成下面这样:

local Circle = class("Circle")
function Circle:ctor(x,y,r) 
	self.x = x
	self.y = y
	self.r = r
end 

function Circle:in_circle(check_x,check_y)
	return (check_x -self.x)^2 + (check_y-self.y)^2 <=self.r^2;
end 

使用传统面向对象的方法之后,我们就可以创建一个指定参数的圆,然后每次去调用圆的in_circle函数就可以了,这样将圆对象化,让这个对象帮我们做判断,参数和过程都极大的简化。但是lua本身就属于精简的语言,我们真的有必要为了一些简单的逻辑,去创建一个类吗?答案是不必的,闭包可以很巧妙的帮我们实现这个问题。下面看一下闭包的实现:

function circle(x,y,r) 
	return function (check_x,check_y)
			  return (check_x -x)^2 + (check_y-y)^2 <=r^2;
		   end 
end

这样,闭包就为我们创建了一个比较抽象但是又是独立的运行环境,其中的upvalue就是x,y,r三个参数,我们指定这三个参数,返回的就是一个包含了这三个参数的闭包函数,我们要做的就是使用这个闭包函数来满足我们的需求

local c1 = circle(1,1,4)
local c2 = circle(3,3,1)
print(c1(1,1))  -->true
print(c2(1,1))  -->false
print(c2(3,3.5)) -->true

这样是不是极大的简化了代码,但是又让编程过程符合面向对象思想

安全沙盒模式下,运行网络代码进行文件读取

1.我们可能会面临一个问题,从网络上down了一份代码在本地运行,但是我们不能保证他们是安全的,比如在文件读取的时候,我们不希望本地的敏感文件被读取。
2.创建一个局部环境,利用闭包修改公用的文件读取

do
	local old_open = io.open 
	local access_ok = function (filename)
		return check_something
	end 
	
	io.open = function(filename) 
		if(access_ok(filename)) then 
			return old_open(filename)
		else
			return nil, "file_denied"
		end 	
	end 
	
	--在这个do---end范围内,down下来的代码利用io.open读取文件时都必须经过检验,
	--通过检验的文件才能被读取,这样可以在不知道代码,并且不改变文件的情况下做到一些安全处理
	
end 
总结

闭包时很好用的技巧,但是要注意不能滥用,尤其时存在大量的upvalue的情况下,因为程序栈会保存这些信息,在闭包函数没有被放弃之前,这些值会一直保留在内存中。当然也不必惧怕使用,因为闭包确实会给我们的编程带来一些很巧妙的构思

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

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值