如何在Lua中注册C函数,但不是在全局上下文中注册,而是作为表字段?
答案 0 :(得分:20)
这是luaL_register()
针对一个或多个功能的意图。规范用法是用C:
/* actual definitions of modA() and modB() are left as an exercise. */
/* list of functions in the module */
static const luaL_reg modfuncs[] =
{
{ "a", modA},
{ "b", modB},
{ NULL, NULL }
};
/* module loader function called eventually by require"mod" */
int luaopen_mod(lua_State *L) {
luaL_register(L, "mod", modfuncs);
return 1;
}
这里创建一个名为“mod”的模块,它有两个名为mod.a
和mod.b
的函数。
引用luaL_register(L,libname,l)
的手册:
只要表位于堆栈的顶部,当
libname
等于时调用NULL
,它只是注册所有 列表l
中的函数(请参阅luaL_Reg
) 进入桌面的顶部 叠加。使用非空
libname
调用时,luaL_register
创建了一个新表t
, 将其设置为全局值 变量libname
,将其设置为值package.loaded[libname]
和。{ 在其上注册所有函数 列表l
。如果有一张桌子package.loaded[libname]
或变量libname
,重复使用此表而不是 创造一个新的。在任何情况下,函数都会将表保留在堆栈顶部。
luaL_register()
就可以通过将NULL
传递给第二个参数来将C函数放入任何表中。
答案 1 :(得分:5)
void register_c_function(char const * const tableName, char const * const funcName, CFunctionSignature funcPointer)
{
lua_getfield(lstate, LUA_GLOBALSINDEX, tableName); // push table onto stack
if (!lua_istable(lstate, -1)) // not a table, create it
{
lua_createtable(lstate, 0, 1); // create new table
lua_setfield(lstate, LUA_GLOBALSINDEX, tableName); // add it to global context
// reset table on stack
lua_pop(lstate, 1); // pop table (nil value) from stack
lua_getfield(lstate, LUA_GLOBALSINDEX, tableName); // push table onto stack
}
lua_pushstring(lstate, funcName); // push key onto stack
lua_pushcfunction(lstate, funcPointer); // push value onto stack
lua_settable(lstate, -3); // add key-value pair to table
lua_pop(lstate, 1); // pop table from stack
}