在C ++中访问Lua函数的返回值,反之亦然

时间:2014-12-09 09:57:57

标签: c++ lua

我在Lua中有一些函数,在C ++中有一些函数,我已经设法从我的加法,幂和除法中得到了正确的结果。我唯一的问题是使用阶乘,因为我无法将正确的数字传递给它,这应该是除法的结果。

在Lua:

function powLua(a, n)
   b = 1
   for i=1,n do b = b * a end
   return b
end

function divisionLua(a, b)
   c = b/a
   return c
end

aLua = additionLua(2, 3)
bLua = additionLua(1, 3)

print("Result of additionLua is a = "..aLua.."\nResult of additionLua is b = "..bLua.."\n")

fac = factorialLua(divLua) <---- this is the part that doesn't work

print("factorial of divLua is "..fac.."\n")

在C ++中:

int addition(lua_State* L)
{
    int x = lua_tonumber(L, 1);
    int y = lua_tonumber(L, 2);

    lua_pushnumber(L, x + y);

    return 1;
}

int fac_calc(int x)
{
    if (x <= 1)
        return 1;

    return x * fac_calc(x-1);
}

int factorial(lua_State* L)
{   
    int fac = lua_tonumber(L, 1);

    lua_pushnumber(L, fac_calc(fac));

    return 1;
}

int power(lua_State* L, int a, int n)
{
    int b;

    lua_getglobal(L, "powLua");
    lua_pushnumber(L, a);
    lua_pushnumber(L, n);

    if (lua_pcall(L, 2, 1, 0) != 0)
        printf("error running function 'powLua': %s", lua_tostring(L, -1));

    if (!lua_isnumber(L, -1))
        printf("function `powLua' must return a number\n");
    b = lua_tonumber(L, -1);
    lua_pop(L, 1);  /* pop returned value */
    return b;
}

int division(lua_State* L, int a, int b)
{
    int c;

    lua_getglobal(L, "divisionLua");
    lua_pushnumber(L, a);
    lua_pushnumber(L, b);

    lua_pcall(L, 2, 1, 0);

    c = lua_tonumber(L, -1);
    lua_pop(L, -1);

    return c;
}

int main(int argc, char* argv[])
{
    lua_State* L = luaL_newstate();

    luaL_openlibs(L); 

    lua_pushcfunction(L, addition); 
    lua_setglobal(L, "additionLua"); 

    lua_pushcfunction(L, factorial);
    lua_setglobal(L, "factorialLua");

    luaL_dofile(L, "test01.lua");

    lua_getglobal(L, "aLua");
    int a = lua_tonumber(L, -1);
    lua_pop(L, -1);

    lua_getglobal(L, "bLua");
    int b = lua_tonumber(L, -1);
    lua_pop(L, -1);

    int pwr = power(L, a, b);

    int div = division(L, a, pwr);
    lua_pushnumber(L, div);
    lua_setglobal(L, "divLua");

    cout << "Result of a^b in powLua is pwr: " << a << "^" << b << " = " << pwr << endl;

    cout << "Result of pwr/a in divisionLua is: " << pwr << "/" << a << " = " << div << endl;

    lua_close(L);
}

我的输出是这样的:

  

addLua的结果是a = 5

     

addLua的结果是b = 4

     

divLua的阶乘是1

     

powLua中的^ b的结果是pwr:5 ^ 4 = 625

     

分区中的pwr / a的结果是:625/5 = 125

我想在打开&#34; test01.lua&#34;之前我必须将分区的结果推到堆栈上。文件,但它也没有工作。

我也通过赋予它直接价值成功地测试了阶乘函数。 例如,factorialLua(5)给出了120的输出。

有人知道我的错误在哪里吗?

修改

设置&#34; divLua&#34;在使用如下测试值运行脚本之前:

int div = 5;
lua_pushnumber(L, div);
lua_setglobal(L, "divLua");
...
...
luaL_dofile(L, "test01.lua");

导致factorialLua(divLua)的正确结果,但是当我设置&#34; divLua&#34;作为division()的值,像这样:

int div = division(L, 5, 30); //div should be 6 now
lua_pushnumber(L, div);
lua_setglobal(L, "divLua");
...
...
luaL_dofile(L, "test01.lua");

factorialLua(divLua)的结果是1,而不是720应该如何。

原因必须是必须在luaL_dofile之后调用division(),但是lua_setglobal(L,&#34; divLua&#34;)必须在它之前。 所以我需要让&#34; div&#34;知道将在稍后完成的计算结果。

有什么建议吗?

1 个答案:

答案 0 :(得分:5)

上面有几个问题:

  • 您尝试在从C ++设置factorialLua(divLua)之前在脚本中计算divLua
  • 您使用负索引调用lua_pop,但它需要一个正整数。
  • 假设解决了前两个问题,那么您正在尝试计算125!,这将是真正大数字。

注意,您当前获得1 factorialLua的原因是因为lua_tonumber如果给定的堆栈索引实际上不是数字,则返回0。由于divLua在调用时仍为nil,因此您实际上正在计算factorialLua(0)

解决此问题的两个明显方法:

  1. 在实际执行脚本之前执行lua_setglobal(L, "divLua")
  2. 将您的阶乘计算移动到C ++域中,实际定义divLua