Am I right to read a nested lua table as argument from C function?

蓝咒 提交于 2020-01-15 19:04:41

问题


I'm going to implement a function with C language and which will be called by Lua script.

This function should receive a lua table(which even contains an array) as the argument, so I should read the fields in the table.I try to do like below, but my function is crashing when I run it. Can anyone help my find the problem?


/*
 function findImage(options)
    imagePath = options.imagePath
    fuzzy = options.fuzzy
    ignoreColors = options.ignoreColor;
    ...
 end

 Call Example:

 findImage {
              imagePath="/var/image.png", 
              fuzzy=0.5,
              ignoreColors={
                             0xffffff, 
                             0x0000ff, 
                             0x2b2b2b
                           }
            }

 */

static int findImgProxy(lua_State *L)
{
    lua_settop(L, 1);
    luaL_checktype(L, 1, LUA_TTABLE);

    lua_getfield(L, -1, "imagePath");
    lua_getfield(L, -2, "fuzzy");
    lua_getfield(L, -3, "ignoreColors");

    const char *imagePath = luaL_checkstring(L, -3);
    double fuzzy    = luaL_optint(L, -2, -1);

    int count  = lua_len(L, -1); // how to get the member count of ignoreColor array

    int colors[count];
    for (int i=0; i count; i++) {
        lua_rawgeti(L, 4, i);
        colors[i] = luaL_checkinteger(L, -1);
        lua_pop(L, 1);
    }

    lua_pop(L, 2);

    ...
    return 1;
}


回答1:


lua_len doesn't return anything, it only pushes the length on the stack. Use this snippet to get the table length:

lua_len(L, -1);
int count = luaL_checkinteger(L, -1);
lua_pop(L, 1);



回答2:


int count  = lua_len(L, -1); // how to get the member count of ignoreColor array

int colors[count];
for (int i=0; i count; i++)
{
    colors[i] = luaL_checkinteger(L, -1-i);
}

The code segment for this looks incorrect (never mind the missing comparision operator in the loop). The correct function for getting the table length is lua_objlen. It looks like you're trying to get the numbers out of 'ignoreColor' but you haven't place them on the stack first. As a result luaL_checkinteger(L, -1-i); ends up accessing the wrong indices on the stack.

You probably want something closer to this for example:

int count  = lua_objlen(L, -1);
std::vector<int> colors(count);
for (int i = 0; i < count; lua_pop(L, 1))
{
  lua_rawgeti(L, 4, ++i);
  colors.push_back( luaL_checkinteger(L, -1) );
}

If you're using Lua 5.2, replace lua_objlen with:

int count  = lua_rawlen(L, -1);

Make sure there's enough space on the stack if you're moving a lot of elements from the table. eg. lua_checkstack



来源:https://stackoverflow.com/questions/18637314/am-i-right-to-read-a-nested-lua-table-as-argument-from-c-function

标签
易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!