首页 | 新闻 | 新品 | 文库 | 方案 | 视频 | 下载 | 商城 | 开发板 | 数据中心 | 座谈新版 | 培训 | 工具 | 博客 | 论坛 | 百科 | GEC | 活动 | 主题月 | 电子展
返回列表 回复 发帖

在可插入脚本的应用程序中嵌入 Lua(1)

在可插入脚本的应用程序中嵌入 Lua(1)

Lua 是一种小型脚本语言。它有多小呢?Lua 使用一个定制模式匹配特性,而不是 POSIX 正则表达式,因为一个完整的正则表达式实现比所有标准的 Lua 库加起来还要大。Lua 提供的字符串匹配要简单得多,它虽然没有 POSIX 那么强大,但大小仅是 POSIX 的一小部分。
Lua 变量不是强类型的;虽然可以检查一个值的类型,但是无法阻止一个变量的类型随着时间而改变。这两点正好适合脚本语言。Lua 的类型系统非常简单,但很灵活。数组和关联数组并合并为一种类型,即 table。string、number(只有浮点数)、boolean 和特殊的 nil 类型都是基本类型。也许更有趣的是,函数(function)也是一种基本类型。就像其他类型一样,可以方便地将函数赋给变量,不需要特殊的语法。另外,Lua 还支持定制的 userdata 对象,开发人员可以通过定义 userdata 对象来处理基本类型以外的其他类型。
对于习惯使用其他语言的程序员来说,Lua 最令人惊讶的地方是,只有 false 和 nil 被看作 false;任何非 boolean 类型的对象总是被看作 true。对于习惯 C 语言的人来说,这有些奇怪,因为在 C 中就可以用 1 和 0 作为 true 和 false。不过这很容易适应。
Lua 是用可移植的 C 编写的。它还可以与 C++ 一起使用,但是核心语言非常易于移植;虽然有少数特性需要借助宿主特性,但是 Lua 可脱离平台依赖良好地运行。Lua 无需进行大量的 autoconf 测试,因为它严格遵从标准。Lua 是在 MIT 许可下发布的,可完全免费用于任何用途,包括商业用途。(因此很多程序员随意将它嵌入到应用程序中)。
为什么嵌入一种语言?嵌入一种脚本语言可以带来很多的好处。我将使用初学 Lua 时用的一个例子:Blizzard 的大规模多玩家在线 RPG,World of Warcraft(WoW)。WoW 的用户界面完全使用 Lua 实现的;开发人员提供一些基本的 API 调用,以便真正与呈现引擎交互,并请求关于世界的数据,然后使用 Lua 作为用户界面代码的核心。
这样一来,将用户界面代码置于沙箱中,使之远离游戏本身的干扰,从而提高安全性和可靠性,这一点就变得容易得多。反过来,这又意味着 Blizzard 可以向玩家开放用户界面,使玩家可以定制代码,改变他们与游戏交互的方式。
通常,对于很多类型的任务,与低级语言相比,脚本语言更易于引入到程序中。具有隐式分配和关联数组特性,并支持垃圾收集的语言,通常有助于更快地开发更简单的代码。它也许没那么快,但是在很多情况下,这并不是问题;例如,用户界面只需要比用户的键盘输入或鼠标动作快就行了。
使用脚本语言有几种方式。第一种方式,也是最简单的方式,是使用它控制一个程序的行为,并使用 C 代码作为一个真正用 Lua 编写的程序的实现细节。第二种方法是主要用 C 编写一个程序,然后使用嵌入的 Lua 来存储和报告数据和配置。第三种方式,也是最灵活的方式,是混合上述两种方式,使用 Lua 脚本编写一些动作,而用 C 代码管理其他部分。Lua 与 C 之间的接口非常简单,因此这种方式非常流行。
编写引擎 对于主要用 Lua 编写的程序,如果 CPU 时间主要用于逐个的操作,顶层控制的分量很轻,那么可以编写一个引擎。这有助于将实现细节与高级设计相分离。用 Lua 而不是 C 来实现程序的核心逻辑可以大大减少开发时间。
对于这种类型的设计,显然期望 Lua-to-C 接口主要由将从 Lua 调用的 C 函数的定义组成,并期望一旦开始执行脚本,将来所有对 C 代码的使用都从脚本中调用。
可编写脚本的配置文件我所知道的每个程序员都至少编写过一段这样的代码,这段代码什么也不做,只是将配置值存储到一个文件中,并在以后恢复那些值。(在我使用过的配置文件当中,Apple 的属性列表也许是我最喜欢的)。但是,可以使用一种嵌入式脚本语言作为这些文件的格式,使用户可以拥有壮观的配置选项阵列。Ion 窗口管理器使用 Lua 作为配置文件,从而使用户可以编写强大而灵活的配置。
对用户来说,最棒的是他们不再局限于简单的赋值;用 Lua 表达的配置文件可以有注释、条件等。可以提供一个优先的 API,用于获取可能影响配置选择的数据。
混合Lua 与 C 之间可以来回嵌套,因为 Lua 解释器是可重入的(reentrant)。如果 C 程序在一个脚本上调用解释器,该脚本调用一个 C 函数,而这个 C 函数又再次使用 Lua 解释器,这是允许的。
World of Warcraft 基本上就是将这样的模型用于它的用户界面;用户界面中的 Lua 调用可以反过来调用引擎,而引擎又将事件交付到用 Lua 编写的用户界面。这样便得到一个灵活的界面,这样的界面具有良好的隔离性和安全性,为用户提供了很大的自主空间,并且缓冲区溢出或崩溃的风险很小。在基于 C 的 API 中,嵌入的代码几乎都会导致崩溃;当使用 Lua 界面时,如果用户界面代码导致崩溃,则存在需要修复的 bug。
返回列表