【发布时间】:2013-07-10 05:56:06
【问题描述】:
我想在 lua 状态上加载一些函数,然后能够从 lua 线程调用这些函数。
我正在尝试在线程上setfenv,以便它们创建的变量仅限于线程,并且不会出现在全局环境中。
lua_State *L = luaL_newstate();
luaL_openlibs(L);
dostring(L, "function f1() my_var = 100 print('var set') end");/* create func on state */
/* ^-- a wrapper which does loadstring + pcall with error handling */
lua_State *l1 = lua_newthread(L);
lua_pushthread(l1); /* l1: t */
lua_newtable(l1); /* l1: t T1{} */
lua_newtable(l1); /* l1: t T1{} T2{} */
lua_getglobal(l1, "_G"); /* l1: t T1{} T2{} _G */
lua_setfield(l1, -2, "__index"); /* l1: t T1{} T2{} ( T2.__index = _G) */
lua_setmetatable(l1, -2); /* l1: t T1 ( T1{}.mt = T2 ) */
if (!lua_setfenv(l1, -2)) /* l1: t (t.fenv = T1) */
printf("setfenv fail!\n");
lua_pop(l1, 1);
dostring(l1, "print('l1: ', my_var)"); /* --> nil (expected) */
dostring(l1, "f1() print('l1: ', my_var)"); /* --> l1: 100 (ok) */
dostring(L, "print('L: ', my_var)"); /* --> L: 100 (No!) */
我在这里做错了吗? (我不想在线程上加载函数,因为它们可能很多,并且 在状态上加载一次似乎是正确的方法)
--编辑--
解决方案,似乎是:
- 为每个线程创建一个新的环境表(使用
__index = _G) - 对于其中运行的每个函数,执行
setfenv(f1, getfenv(0))
【问题讨论】:
-
你使用的 Lua 版本是什么?
-
我正在使用 LuaJIT-2.0.2(即 Lua5.1 + AFAIK 的一些扩展)
标签: c lua environment-variables lua-5.1