第一版是为 Lua 5.0 撰写的。虽然在很大程度上仍然适用于后续版本,但有一些差异。
第四版针对 Lua 5.3,可在 亚马逊 和其他书店购买。
购买本书,您还将帮助支持 Lua 项目。
![]() |
用 Lua 编程 | ![]() |
| 第四部分。C API 第 25 章。扩展您的应用程序 |
Lua 的一个重要用途是作为配置语言。在本章中,我们将说明如何使用 Lua 来配置程序,从一个简单的示例开始,然后逐步扩展它来执行更复杂的任务。
作为我们的第一个任务,让我们设想一个简单的配置场景:您的 C 程序(我们称之为pp)有一个窗口,您希望用户能够指定初始窗口大小。显然,对于如此简单的任务,有几个选项比使用 Lua 更简单,例如环境变量或带有名称-值对的文件。但即使使用一个简单的文本文件,您也必须以某种方式解析它;因此,您决定使用 Lua 配置文件(即碰巧是 Lua 程序的纯文本文件)。在其最简单的形式中,此文件可以包含类似于以下几行的内容
-- configuration file for program `pp'
-- define window size
width = 200
height = 300
现在,您必须使用 Lua API 指示 Lua 解析此文件,然后获取全局变量width和height的值。以下函数可以完成此工作
#include <lua.h>
#include <lauxlib.h>
#include <lualib.h>
void load (char *filename, int *width, int *height) {
lua_State *L = lua_open();
luaopen_base(L);
luaopen_io(L);
luaopen_string(L);
luaopen_math(L);
if (luaL_loadfile(L, filename) || lua_pcall(L, 0, 0, 0))
error(L, "cannot run configuration file: %s",
lua_tostring(L, -1));
lua_getglobal(L, "width");
lua_getglobal(L, "height");
if (!lua_isnumber(L, -2))
error(L, "`width' should be a number\n");
if (!lua_isnumber(L, -1))
error(L, "`height' should be a number\n");
*width = (int)lua_tonumber(L, -2);
*height = (int)lua_tonumber(L, -1);
lua_close(L);
}
首先,它打开 Lua 包并加载标准库(它们是可选的,但通常最好备用)。然后,它使用luaL_loadfile从文件filename加载块,并调用lua_pcall来运行它。如果在任何这些函数中出现错误(例如,配置文件中的语法错误),则调用将返回一个非零错误代码并将错误消息推送到堆栈。与往常一样,我们的程序使用带有索引-1的lua_tostring从堆栈顶部获取消息。(我们在第 24.1 节中定义了error函数。)
在运行块之后,程序需要获取全局变量的值。为此,它调用两次lua_getglobal,其唯一参数(除了无所不在的lua_State)是变量名。每个调用将相应的全局值推送到堆栈顶部,以便宽度位于索引-2,高度位于索引-1(顶部)。(因为堆栈之前是空的,所以您还可以从底部索引,从第一个值使用1,从第二个值使用2。但是,通过从顶部索引,即使堆栈不为空,您的代码也能正常工作。)接下来,我们的示例使用lua_isnumber来检查每个值是否为数字。然后,它使用lua_tonumber将此类值转换为double,而 C 将其强制转换为int。最后,它关闭 Lua 状态并返回。
是否值得使用 Lua?正如我之前所说的,对于如此简单的任务,一个只包含两个数字的简单文件比 Lua 要容易使用得多。即便如此,使用 Lua 也带来了一些优势。首先,Lua 为你处理所有语法细节(和错误);你的配置文件甚至可以有注释!其次,用户已经能够使用它进行更复杂的配置。例如,脚本可以提示用户提供一些信息,或者可以查询环境变量以选择合适的大小
-- configuration file for program `pp'
if getenv("DISPLAY") == ":0.0" then
width = 300; height = 300
else
width = 200; height = 200
end
即使在如此简单的配置场景中,也很难预料用户想要什么;但只要脚本定义了这两个变量,你的 C 应用程序就可以在不进行更改的情况下工作。
使用 Lua 的最后原因是现在可以轻松地为你的程序添加新的配置功能;这种轻松性创造了一种态度,从而产生更灵活的程序。
| 版权所有 © 2003–2004 Roberto Ierusalimschy。保留所有权利。 | ![]() |