Lua 作为一个运行效率非常高的脚本语言,简单方便,如今很多游戏开发都会用到。今天研究下 c++ 和 lua 是如何交互的~

# 1.c++ 调用 lua

我是在 macos 上实验的,过程应该和 linux 上类似。使用的 lua 版本是 5.3.0.

c++ 调用 lua 原理主要是通过 Lua 的堆栈,一方将传递的参数以及参数个数压入栈中,另一方则在栈中取出参数,并将返回值压入栈中,由另一方取出,实现交互。这个过程和 c++ 和汇编 (如 nasm) 的交互过程很像.

# (i). 添加依赖

将 liblua.a 添加到项目中:

lib

设置 search paths:

Header Search Paths 设置为 lua 安装位置,用来搜索头文件.

Library Search Paths 设置为项目存放.a 库的目录.

lib

# (ii). 代码测试

#include <iostream>
extern "C" {
#include "lua.h"
#include "lualib.h"
#include "lauxlib.h"
}
using namespace std;
int main()
{
    //1. 创建一个 state
    lua_State *L = luaL_newstate();
    //2. 入栈操作
    lua_pushstring(L, "Hello World~");
    //3. 取值操作
    if (lua_isstring(L, 1)) { // 判断是否可以转为 string
        cout << lua_tostring(L, 1) << endl; // 转为 string 并返回
    }
    //4. 关闭 state
    lua_close(L);
}

# (iii). 运行代码

运行结果:

lib

# (iv). 求和代码:

lua 代码:

a
function Sum(a, b)
  return (a+b);
end

c++ 代码:

#include <iostream>
extern "C" {
#include "lua.h"
#include "lualib.h"
#include "lauxlib.h"
}
using namespace std;
int main()
{
    // 创建 Lua 状态
    lua_State *L = luaL_newstate();
    if (L == NULL)
    {
        return 0;
    }
    
    // 加载 Lua 文件
    int bRet = luaL_loadfile(L, "sum.lua");
    if (bRet)
    {
        cout << "load file error" << endl;
        return 0;
    }
    
    // 运行 Lua 文件
    bRet = lua_pcall(L, 0, 0, 0);
    if (bRet)
    {
        cout << "pcall error" << endl;
        return 0;
    }
    // 读取函数
    lua_getglobal(L, "Sum");        // 获取函数,压入栈中
    lua_pushinteger(L, 10);          // 压入参数
    lua_pushinteger(L, 8);          // 压入参数
    int iRet = lua_pcall(L, 2, 1, 0);// 调用函数,调用完成以后,会将返回值压入栈中,第一个 2 表示参数个数,第二个 1 表示返回结果个数。
    if (iRet)                       // 调用出错
    {
        const char *pErrorMsg = lua_tostring(L, -1);
        cout << pErrorMsg << endl;
        lua_close(L);
        return 0;
    }
    if (lua_isinteger(L, -1))        // 取值输出
    {
        int sum = lua_tointeger(L, -1);
        cout << sum << endl;
    }
    
    // 关闭 state
    lua_close(L);
    return 0;
}

结果:

sum

# 2.lua 调用 c++

lua 调用 c++ 原理主要是将 c++ 代码编译成.so 动态库,然后在 lua 中用 require 引入,从而调用。通信还是通过 lua 栈来实现的。这里就不展开了。具体可以参考 lua 官方文档,还有 lua5.3 中文文档

# 3.LuaTinker

以上介绍的都是 lua 官方的提供给 c 的一些 api, 较为底层,其实有很多 c++ 和 lua 代码的绑定库,将以上的栈操作以及函数注册等封装了起来,如 LuaBind,LuaTinker 等,我们的项目中使用的就是 LuaTinker.LuaTinker 使用方法可以在 git 仓库中查看.

更新于 阅读次数

请我喝[茶]~( ̄▽ ̄)~*

Nirvana 支付宝

支付宝