美文网首页
C模块回调Lua函数的两种方法

C模块回调Lua函数的两种方法

作者: 偶是星爷 | 来源:发表于2015-11-07 08:15 被阅读441次

lua和C通过虚拟栈这种交互方式简单而又可靠,缺点就是C做栈平衡稍微会多写一点代码。
今天分享学到的C模块回调Lua函数的两种方法,都是炒冷饭,大侠勿喷。

1. C保存函数对象

C模块可以通过注册表保存Lua里面的对象,等适当时候取出再调用即可。

static int lua_callback = LUA_REFNIL;

static int setnotify(lua_State *L)
{
  lua_callback = luaL_ref(L, LUA_REGISTRYINDEX);
  return 0;
}

static int testnotify(lua_State *L)
{
  lua_rawgeti(L, LUA_REGISTRYINDEX, lua_callback);
  lua_call(L, 0, 0);
}

luaL_ref把栈顶的值取出,方的指定的tabel中,然后返回一个索引(目测是数组的index)。
lua_rawgeti把之前保存的function对象取出,再由lua_call调用。

function callback(  )
        print "Callback"
end

cb.setnotify(callback)
cb.testnotify()

2. C访问Lua全局环境

第二种方法更简便,C自己直接Lua中的函数,就像Lua调用C一样

static int testenv(lua_State *L)
{
  lua_getglobal(L, "defcallback");
  lua_call(L, 0, 0);
}

该方法的缺点就是如果C模块独立编写,方法名就不太灵活。
用这种方法一般会在Lua端再封装一层,以隔离全局环境。

3. 完整例子


#include <stdio.h>
#include <stdlib.h>
#include "lua.h"
#include "lualib.h"
#include "lauxlib.h"

static int lua_callback = LUA_REFNIL;

static int setnotify(lua_State *L)
{
  printf("111 %d\n", lua_callback);
  lua_callback = luaL_ref(L, LUA_REGISTRYINDEX);
  printf("111 %d\n", lua_callback);
  return 0;
}

static int testnotify(lua_State *L)
{
  lua_rawgeti(L, LUA_REGISTRYINDEX, lua_callback);
  lua_call(L, 0, 0);
}

static int testenv(lua_State *L)
{
  lua_getglobal(L, "defcallback");
  lua_call(L, 0, 0);
}

static const luaL_Reg cblib[] = {
  {"setnotify", setnotify},
  {"testnotify", testnotify},
  {"testenv", testenv},
  {NULL, NULL}
};

int luaopen_cb(lua_State *L)
{
  luaL_register(L, "cb", cblib);
  return 1;
}
{% endcodeblock %}

{% codeblock test.lua lang:lua %}

require("cb")

function callback(  )
  print "Callback"
end

function defcallback()
  print "Predef callback"
end

cb.setnotify(callback)
cb.testnotify()
print "Done"
cb.testenv()

相关文章

  • C模块回调Lua函数的两种方法

    lua和C通过虚拟栈这种交互方式简单而又可靠,缺点就是C做栈平衡稍微会多写一点代码。今天分享学到的C模块回调Lua...

  • C Lua API-栈

    简介 C API 是一组能使用C代码与Lua交互的函数。其中包括读写Lua全局变量、调Lua函数、运行一段Lua代...

  • lua和c的初始

    lua和c的交互包括:c访问lua的变量、c访问lua的table、c调用lua的方法、lua调用c的函数 参考链...

  • python 异步IO

    线程池的使用+requests模块+回调函数 进程池的使用+requests模块+回调函数 asyncio + a...

  • Lua与C++如何相互交互?

    Lua与C++如何相互交互 通过lua虚拟栈隔离Lua和C/C++类型和彼此内存的差异来实现数据及函数互相调拥。1...

  • 同步,异步

    js异步操作的方法:1.回调函数就是把一方法当作参数传到另一个方法里。有两种回调方式:同步回调和有异步回调 同步回...

  • 富文本响应url整体设计思路

    c++的实现细节 handleOpenUrl为a标签点击后的回调函数 lua层使用 注意第三个参数 封装1:没有地...

  • Android使用suspendCancellableCorou

    普通的回调函数: 回调方法,模拟耗时操作 去掉回调,转换为挂起函数:

  • 前端入门11 -- JavaScript之Promise

    回调函数 回调函数分为两种类型,分别为同步回调与异步回调; 同步回调:会立即执行,完全执行完了才结束,不会放入回调...

  • Lua源码模块分析

    这些模块实现实用功能: ldebug.c - 调试接口。包括访问调试挂钩的函数(lua_sethook,lua_g...

网友评论

      本文标题:C模块回调Lua函数的两种方法

      本文链接:https://www.haomeiwen.com/subject/rnuchttx.html