我试图将一个Lua类对象推入堆栈。指向该对象的指针可以由多个函数返回。Lua userdata对象管理
换句话说:我需要推送userdata值,同时仍然保持对它们使用'==','〜='等的能力,所以如果它的相同C++对象的userdata指针必须相同。
-- this should push the object onto the stack
local firstObject = GetClassObject();
firstObject:doSomething();
firstObject将由LUA脚本存储后来在代码中,我需要再次做到这一点:
-- the c++ class pointer has not changed here
-- so I would like to push the same userdata pointer as in the first call...
local object = GetClassObject();
-- if I would not do this the following here would fail... :C
if object == firstObject then
...
我的Push功能应主要检查是否已经有相同的C++类的指针某处并推动相关的用户数据指针,如果是这样的话(无论我如何推它,对象应该工作1:1相同)
如果不是,它应该创建一个新的userdata(将它推入堆栈)并设置它到类对象。
这里是我的代码:
template <typename T>
void Push(const T &tObject)
{
lua_State *L = GetLuaState();
// Here i need to check if such a C++ object (the same tObject)
// already exists!
//
// If so i want to push the associated userdata.
// Object didn't exist yet -> we need a new userdata
void *pUserData = lua_newuserdata(L, sizeof(tObject));
*reinterpret_cast<T*>(pUserData) = tObject;
}
template <typename T>
void Push(const T &tObject, const char *pszTable)
{
Push(tObject);
lua_State *L = GetLuaState();
luaL_getmetatable(L, pszTable);
lua_setmetatable(L, -2);
}
template <typename T>
T& Get(int nIndex)
{
T *pUserData = reinterpret_cast<T*>(lua_touserdata(GetLuaState(), nIndex));
if(pUserData == nullptr)
throw std::exception("Invalid userdata!");
return *pUserData;
}
template <typename T>
T& Get(int nIndex, const char *pszTable)
{
T *pUserData = reinterpret_cast<T*>(LuaToUData(nIndex, pszTable));
if(pUserData == nullptr)
throw std::exception("Invalid userdata!");
return *pUserData;
}
LuaToUData是自己的功能,我写的不是抛出一个LUA错误:
void* LuaToUData(int nIndex, const char *pszTable)
{
void *pUserData = lua_touserdata(g_luaState, nIndex);
if(pUserData != nullptr)
{
if(lua_getmetatable(g_luaState, nIndex) != 0)
{
lua_getfield(g_luaState, LUA_REGISTRYINDEX, pszTable);
bool bEqual = (lua_rawequal(g_luaState, -1, -2) == 1);
lua_pop(g_luaState, 2);
if(bEqual)
return pUserData;
}
}
return nullptr;
}
我发现很难找出你在这里想要做什么。你只是试图缓存一个lua userdata实例创建后? – Rook
我试图推动userdata值,同时仍然保持对它们使用'==','〜='等的能力,所以如果它的相同C++对象的userdata指针必须是相同的。 – user1478081
Lua userdata对象在内部通过引用进行比较。从相同的基础指针创建的两个userdata实例应该相等比较。你是说在这种情况下'=='不起作用吗?你有没有重写'__eq' metatable条目? – Rook