当数据不是Lua的标准类型(数字,字符串,bool等)时,通常只会推送'userdata'。
但是你如何将实际的Function指针推送到Lua(而不是userdata;因为userdata在Lua中不能作为函数执行),假设函数看起来像这样:
void nothing(const char* stuff)
{
do_magic_things_with(stuff);
}
返回的值应该与此本机Lua函数的返回值相似:
function things()
return function(stuff)
do_magic_things_with(stuff)
end
end
这可能与C API有关吗?如果是,如何(例子将被赞赏)?
编辑:为了增加一些清晰度,该值应该由通过C API向Lua公开的函数返回。
答案 0 :(得分:10)
示例包含在PiL
中这是一个遵循当前接受的答案形式的示例。
#include <lua.h>
#include <lualib.h>
#include <lauxlib.h>
#include <stdio.h>
/* this is the C function you want to return */
static void
cfunction(const char *s)
{
puts(s);
}
/* this is the proxy function that acts like cfunction */
static int
proxy(lua_State *L)
{
cfunction(luaL_checkstring(L, 1));
return 0;
}
/* this global function returns "cfunction" to Lua. */
static int
getproxy(lua_State *L)
{
lua_pushcfunction(L, &proxy);
return 1;
}
int
main(int argc, char **argv)
{
lua_State *L;
L = luaL_newstate();
/* set the global function that returns the proxy */
lua_pushcfunction(L, getproxy);
lua_setglobal(L, "getproxy");
/* see if it works */
luaL_dostring(L, "p = getproxy() p('Hello, world!')");
lua_close(L);
return 0;
}
答案 1 :(得分:1)
您可以通过__call
元方法返回带有代理您的C函数的元表的userdata。这样,userdata可以像函数一样被调用。以下是完整的程序示例。
#include <lua.h>
#include <lualib.h>
#include <lauxlib.h>
#include <stdio.h>
/* this is the C function you want to return */
static void
cfunction(const char *s)
{
puts(s);
}
/* this is the proxy function that will be used as the __call metamethod */
static int
proxy(lua_State *L)
{
luaL_checkudata(L, 1, "proxy");
cfunction(luaL_checkstring(L, 2));
return 0;
}
/* this global function returns the C function with a userdata proxy */
static int
getproxy(lua_State *L)
{
lua_newuserdata(L, sizeof (int));
luaL_getmetatable(L, "proxy");
lua_setmetatable(L, -2);
return 1;
}
int
main(int argc, char **argv)
{
lua_State *L;
L = luaL_newstate();
/* create the proxy metatable */
luaL_newmetatable(L, "proxy");
lua_pushcfunction(L, proxy);
lua_setfield(L, -2, "__call");
/* set the global function that returns the proxy */
lua_pushcfunction(L, getproxy);
lua_setglobal(L, "getproxy");
/* see if it works */
luaL_dostring(L, "p = getproxy() p('Hello, world!')");
lua_close(L);
return 0;
}
回想起来,我完全没想到你在问什么。您真正需要做的就是创建一个类型为lua_CFunction的函数,该函数从Lua堆栈中提取参数并将它们传递给目标C函数。上面的代码从字面上回答了你的问题,但对你真正需要完成的事情来说可能有些过分。