C/C++ 与 Lua 互相调用详解

Lua 是一门轻量级、嵌入式的脚本语言,常常与 C/C++ 结合使用。通过嵌入 Lua,可以让应用程序获得灵活的配置、脚本化逻辑和可扩展性。

本文将介绍如何在 C/C++ 调用 Lua 函数 ,以及如何让 Lua 调用 C/C++ 函数 。最后给出一个 完整的示例工程,可以直接编译运行。


一、C 调用 Lua

Lua 脚本(script.lua):

Lua 复制代码
-- 定义一个 Lua 函数
function add(a, b)
    return a + b
end

C++ 代码调用:

cpp 复制代码
lua_getglobal(L, "add");   // 获取 Lua 中的函数
lua_pushnumber(L, 10);     // 压入参数
lua_pushnumber(L, 20);

if (lua_pcall(L, 2, 1, 0) != 0) {
    std::cerr << "Error: " << lua_tostring(L, -1) << std::endl;
}

double result = lua_tonumber(L, -1); // 获取返回值
lua_pop(L, 1);                       // 弹出栈顶

运行后会输出 30


二、Lua 调用 C/C++

Lua 可以调用在 C/C++ 里注册的函数。

C++ 代码:

cpp 复制代码
int cpp_multiply(lua_State* L) {
    int a = luaL_checkinteger(L, 1);
    int b = luaL_checkinteger(L, 2);
    lua_pushinteger(L, a * b);
    return 1; // 返回值数量
}

注册函数:

cpp 复制代码
lua_register(L, "cpp_multiply", cpp_multiply);

Lua 调用:

Lua 复制代码
print("cpp_multiply result:", cpp_multiply(6, 7))

运行后会输出 42


三、完整示例工程

目录结构

bash 复制代码
demo-lua/
├── CMakeLists.txt
├── main.cpp
└── script.lua

1. CMakeLists.txt

bash 复制代码
cmake_minimum_required(VERSION 3.10)
project(demo-lua CXX)

set(CMAKE_CXX_STANDARD 11)

# 查找 Lua
find_package(PkgConfig REQUIRED)
pkg_search_module(LUA REQUIRED lua5.3)

include_directories(${LUA_INCLUDE_DIRS})
link_directories(${LUA_LIBRARY_DIRS})

add_executable(demo main.cpp)
target_link_libraries(demo ${LUA_LIBRARIES})

2. script.lua

Lua 复制代码
-- Lua 脚本文件

-- 定义函数
function add(a, b)
    return a + b
end

-- 调用 C++ 注册的函数
function test_cpp_func()
    local res = cpp_multiply(6, 7)
    print("cpp_multiply result from Lua:", res)
end

3. main.cpp

cpp 复制代码
#include <iostream>
#include <lua.hpp>

// C++ 函数:在 Lua 中注册为 cpp_multiply
int cpp_multiply(lua_State* L) {
    int a = luaL_checkinteger(L, 1);
    int b = luaL_checkinteger(L, 2);
    lua_pushinteger(L, a * b);
    return 1;
}

int main() {
    lua_State* L = luaL_newstate();   // 创建 Lua 虚拟机
    luaL_openlibs(L);                 // 打开标准库

    // 注册 C++ 函数到 Lua
    lua_register(L, "cpp_multiply", cpp_multiply);

    // 加载 Lua 脚本
    if (luaL_dofile(L, "script.lua")) {
        std::cerr << "Failed to load script.lua: "
                  << lua_tostring(L, -1) << std::endl;
        lua_close(L);
        return 1;
    }

    // 调用 Lua 的 add() 函数
    lua_getglobal(L, "add");
    lua_pushnumber(L, 10);
    lua_pushnumber(L, 20);
    if (lua_pcall(L, 2, 1, 0) != 0) {
        std::cerr << "Error running add(): "
                  << lua_tostring(L, -1) << std::endl;
        lua_close(L);
        return 1;
    }
    double result = lua_tonumber(L, -1);
    lua_pop(L, 1);
    std::cout << "Result from Lua add(): " << result << std::endl;

    // 调用 Lua 的 test_cpp_func()
    lua_getglobal(L, "test_cpp_func");
    if (lua_pcall(L, 0, 0, 0) != 0) {
        std::cerr << "Error running test_cpp_func(): "
                  << lua_tostring(L, -1) << std::endl;
    }

    lua_close(L);
    return 0;
}

四、构建与运行

bash 复制代码
# 编译
mkdir build && cd build
cmake ..
make

# 运行
./demo

五、运行效果

复制代码
相关推荐
疏狂难除1 天前
windows上使用LLVM编译lua
开发语言·lua
IMPYLH2 天前
Lua 的 Math(数学) 模块
开发语言·笔记·lua
脸大是真的好~3 天前
分布式锁-基于redis实现分布式锁(不推荐)- 改进利用LUA脚本(不推荐)前面都是原理 - Redisson分布式锁
redis·分布式·lua
ChaITSimpleLove4 天前
基于 .NET Garnet 1.0.91 实现高性能分布式锁(使用 Lua 脚本)
分布式·.net·lua
羑悻的小杀马特4 天前
Lua vs C++:核心设计哲学差异——从“系统基石”到“灵活工具”的思维碰撞
c++·lua
小毅&Nora4 天前
【后端】【工具】Redis Lua脚本漏洞深度解析:从CVE-2022-0543到Redis 7.x的全面防御指南
redis·安全·lua
古城小栈4 天前
接口测试:Postman+Newman 自动化脚本实战指南
自动化·lua·postman
小坏讲微服务4 天前
Spring Boot4.0 集成 Redis 实现看门狗 Lua 脚本分布式锁完整使用
java·spring boot·redis·分布式·后端·lua
IMPYLH5 天前
Lua 的 IO (输入/输出)模块
开发语言·笔记·后端·lua
菠萝地亚狂想曲5 天前
使用C语言操作LUA栈
c语言·junit·lua