Правильно ли я читать вложенную таблицу lua в качестве аргумента функции C?

Я собираюсь реализовать функцию на языке Си, которая будет вызываться скриптом Lua.

Эта функция должна получить таблицу lua (которая даже содержит массив) в качестве аргумента, поэтому я должен прочитать поля в таблице. Я пытаюсь сделать, как показано ниже, но моя функция падает, когда я запускаю ее. Может кто-нибудь помочь мне найти проблему?


/*
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 ничего не возвращает, он только увеличивает длину стека. Используйте этот фрагмент, чтобы получить длину таблицы:

lua_len(L, -1);
int count = luaL_checkinteger(L, -1);
lua_pop(L, 1);
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++)
{
colors[i] = luaL_checkinteger(L, -1-i);
}

Сегмент кода для этого выглядит неправильно (не говоря уже о пропущенном операторе сравнения в цикле). Правильная функция для получения длины таблицы lua_objlen, Похоже, вы пытаетесь получить числа из «ignoreColor», но вы сначала не поместили их в стек. В следствии luaL_checkinteger(L, -1-i); заканчивается доступ к неправильные показатели в стеке.

Вы, вероятно, хотите что-то ближе к этому, например:

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) );
}

Если вы используете Lua 5.2, замените lua_objlen с:

int count  = lua_rawlen(L, -1);

Убедитесь, что в стеке достаточно места, если вы перемещаете много элементов из таблицы. например. lua_checkstack

1

По вопросам рекламы [email protected]