比较权威的房产网站,合肥瑶海区地图全图高清版,小说网站用什么虚拟主机,微微网站建设环境#xff08;Environment#xff09;
具有动态名称的全局变量 全局变量的声明
由于Lua语言将全局变量存放在一个普通的表中#xff0c;所以可以通过元表来发现访问不存在全局变量的情况。 正如前面所提到的#xff0c;我们不允许值为nil的全局变量#xff0c;因为值为…环境Environment
具有动态名称的全局变量 全局变量的声明
由于Lua语言将全局变量存放在一个普通的表中所以可以通过元表来发现访问不存在全局变量的情况。 正如前面所提到的我们不允许值为nil的全局变量因为值为nil的全局变量都会被自动地认为是未声明的。但是要允许值为nil的全局变量也不难只需要引入一个辅助表来保存已声明变量的名称即可。一旦调用了元方法元方法就会检查该表看变量是否是未声明过的。最终的代码可能与示例22.2中的代码类似。 现在即使像xnil这样的赋值也能够声明全局变量了。
非全局环境
在Lua语言中全局变量并不一定非得是真正全局的。Lua语言竭尽全力地让程序员有全局变量存在的幻觉
一个自由名称free name是指没有关联到显式声明上的名称即它不出现在对应局部变量的范围内。例如在下面的代码段中x和y是自由名称而z则不是 Lua语言把所有的代码段都当作匿名函数。所以Lua语言编译器实际上将原来的代码段编译为如下形式也就是说Lua语言是在一个名为_ENV的预定义上值一个外部的局部变量upvalue存在的情况下编译所有的代码段的。因此所有的变量要么是绑定到了一个名称的局部变量要么是_ENV中的一个字段而_ENV本身是一个局部变量一个上值。 _ENV的初始值可以是任意的表实际上也不用一定是表我们会在后续讨论。任何一个这样的表都被称为一个环境。为了维持全局变量存在的幻觉Lua语言在内部维护了一个表来用作全局环境global environment。通常当加载一个代码段时函数load会使用预定义的上值来初始化全局环境。因此原始的代码段等价于 Lua语言中处理全局变量的方式
•编译器在编译所有代码段前在外层创建局部变量_ENV
•编译器将所有自由名称var变换为_ENV.var
•函数load或函数loadfile使用全局环境初始化代码段的第一个上值即Lua语言内部维护的一个普通的表。
使用_ENV 环境和模块
函数load通常把被加载代码段的上值_ENV初始化为全局环境。不过函数load还有一个可选的第四个参数来让我们为_ENV指定一个不同的初始值。 垃圾收集
弱引用表weak table、析构器finalizer和函数collectgarbage是在Lua语言中用来辅助垃圾收集器的主要机制。弱引用表允许收集Lua语言中还可以被程序访问的对象析构器允许收集不在垃圾收集器直接控制下的外部对象函数collectgarbage则允许我们控制垃圾收集器的步长。
弱引用表
简单地清除引用可能还不够。在有些情况下还需要程序和垃圾收集器之间的协作。一个典型的例子是当我们要保存某些类型例如文件的活跃对象的列表时。这个需求看上去很简单我们只需要把每个新对象插入数组即可但是一旦一个对象成为了数组的一部分它就再也无法被回收了虽然已经没有其他任何地方在引用它但数组依然在引用它。除非我们告诉Lua语言数组对该对象的引用不应该阻碍对此对象的回收否则Lua语言本身是无从知晓的。
弱引用表就是这样一种用来告知Lua语言一个引用不应阻止对一个对象回收的机制。所谓弱引用weak reference是一种不在垃圾收集器考虑范围内的对象引用。如果对一个对象的所有引用都是弱引用那么垃圾收集器将会回收这个对象并删除这些弱引用。Lua用语言通过弱引用表实现弱引用弱引用表就是元素均为弱引用的表这意味着如果一个对象只被一个弱引用表持有那么Lua语言最终会回收这个对象。
表由键值对组成其两者都可以容纳任意类型的对象。在正常情况下垃圾收集器不会回收一个在可访问的表中作为键或值的对象。也就是说键和值都是强strong引用它们会阻止对其所指向对象的回收。在一个弱引用表中键和值都可以是弱引用的。这就意味着有三种类型的弱引用表即具有弱引用键的表、具有弱引用值的表及同时具有弱引用键和值的表。不论是哪种类型的弱引用表只要有一个键或值被回收了那么对应的整个键值对都会被从表中删除。
一个表是否为弱引用表是由其元表中的__mode字段所决定的。当这个字段存在时其值应为一个字符串如果这个字符串是k那么这个表的键是弱引用的如果这个字符串是v那么这个表的值是弱引用的如果这个字符串是kv那么这个表的键和值都是弱引用的。 在本例中第二句赋值key{}覆盖了指向第一个键的索引。调用collectgarbage强制垃圾收集器进行一次完整的垃圾收集。由于已经没有指向第一个键的其他引用因此Lua语言会回收这个键并从表中删除对应的元素。然而由于第二个键仍然被变量key所引用因此Lua不会回收它。
请注意只有对象可以从弱引用表中被移除而像数字和布尔这样的“值”是不可回收的。例如如果我们在表a之前的示例中插入一个数值类型的键那么垃圾收集器永远不会回收它。当然如果在一个值为弱引用的弱引用表中一个数值类型键相关联的值被回收了那么整个元素都会从这个弱引用表中被删除。
记忆函数Memorize Function
我们可以通过记忆memorize函数的执行结果在后续使用相同参数再次调用该函数时直接返回之前记忆的结果来加快函数的运行速度 对象属性Object Attribute
弱引用表的另外一种重要应用是将属性与对象关联起来。在各种各样的情况下我们都需要把某些属性绑定到某个对象例如函数名、表的默认值及数组的大小等。
瞬表
在Lua语言中一个具有弱引用键和强引用值的表是一个瞬表。在一个瞬表中一个键的可访问性控制着对应值的可访问性。更确切地说考虑瞬表中的一个元素k,v指向的v的引用只有当存在某些指向k的其他外部引用存在时才是强引用否则即使v直接或间接地引用了k垃圾收集器最终会收集k并把元素从表中移除。
析构器Finalizer
虽然垃圾收集器的目标是回收对象但是它也可以帮助程序员来释放外部资源。出于这种目的几种编程语言提供了析构器。析构器是一个与对象关联的函数当该对象即将被回收时该函数会被调用。