lua C语言api学习3 lua中调用C语言函数

发布于:2025-03-17 ⋅ 阅读:(19) ⋅ 点赞:(0)

本文介绍如何在lua中如何调用自定义C语言函数

1 C函数要求

Lua可以调用C语言函数,但这并不意味着Lua可以调用所有的C函数。当Lua调用C函数时,这个C函数必须遵循某种规则来获取参数和返回结果。此外,当Lua调用C函数时,我们必须注册该函数,即必须以一种恰当的方式为Lua提供该C 函数的地址。所有在lua中注册的函数必须遵循下面原型。

typedef int (*lua_CFunction) (lua_State * L);

举例如下,

// 定义C函数,参数必须为lua_State* L状态,
// 返回值为lua函数test的返回值数量,为0.
static int test( lua_State* L){
	printf("使用lua调用C函数test成功\n");
	return 0;
}

2 注册一个C函数

定义好一个C函数后,需使用lua_register函数进行注册后,才能在lua语言中使用。lua_register格式要求如下。

void lua_register (lua_State *L, const char *name, lua_CFunction f);

举例如下,

//04注册一个C函数.c
#include <stdio.h>
#include <stdlib.h>

// Lua数据类型与函数接口
#include "lua.h" 
// Lua与C交互辅助函数接口    
#include "lauxlib.h" 
// Lua标准库打开接口
#include "lualib.h"  


// 定义C函数,参数必须为lua_State* L状态,
// 返回值为lua函数test的返回值数量,为0.
static int C_test( lua_State* L){
	printf("使用lua调用C函数C_test成功\n");
	return 0;
}


int main()
{
    // 创建Lua状态
    lua_State* L = luaL_newstate();           
    // 打开标准库
    luaL_openlibs(L);  
	// 注册C函数test为lua函数test
	lua_register(L,"test",C_test);
    // 解析并执行Lua脚本字符串
	luaL_dostring(L,"test()");
	
    // 关闭Lua线程
    lua_close(L);                             
    return 0;
}

运行结果如下,
在这里插入图片描述

3 C语言与lua语言参数传递

上面例子中lua语言调用C函数test,中间没包含参数传递,即函数test既没有参数输入也没有返回值,比较简单。C语言与lua语言参数传递需使用到虚拟栈 lua_State* L进行交换。举例如下,
lua调用

-- add为一个用C函数C_add定义的函数
-- 当在lua执行下面函数add时,lua语言会将参数7,2,5按顺序压入虚拟栈L,再调用C函数C_add,
-- 后根据C函数C_add的返回值,将栈顶弹出传递给lua语言,赋值给变量a
a=add(7,2,5)

C函数C_add定义如下

// 定义C函数,参数必须为lua_State* L状态
static int C_add( lua_State* L){
	printf("使用lua调用C函数C_add成功\n");
	//使用lua_tointeger按索引获取栈L的元素
	//索引1为函数参数1,2为函数参数2,以此类推.
	//lua传递参数给C语言需进行数据转换,
	//因为这个函数参数均为整数,所以使用lua_tointeger
	//若其他数据类型,需使用类似的lua_to*函数
	int a1 = lua_tointeger(L,1);
	int a2 = lua_tointeger(L,2);
	int a3 = lua_tointeger(L,3);
	//打印各个参数的值
	printf("第1个参数=%d\n",a1);
	printf("第2个参数=%d\n",a2);
	printf("第3个参数=%d\n",a3);
	//将三个参数值相加并压入栈
	//使用lua_pushinteger函数将整数值压入,其他数据类型需使用类似lua_push*函数
	//若有多个返回值,按顺序压入栈
	lua_pushinteger(L,a1+a2+a3);
	// 返回值为lua函数add的返回值数量,为1.
	return 1;
}

整理成C代码

//05lua和C语言参数传递.c
#include <stdio.h>
#include <stdlib.h>

// Lua数据类型与函数接口
#include "lua.h" 
// Lua与C交互辅助函数接口    
#include "lauxlib.h" 
// Lua标准库打开接口
#include "lualib.h"  


// 定义C函数,参数必须为lua_State* L状态
static int C_add( lua_State* L){
	printf("使用lua调用C函数C_add成功\n");
	//使用lua_tointeger按索引获取栈L的元素
	//索引1为函数参数1,2为函数参数2,以此类推.
	//lua传递参数给C语言需进行数据转换,
	//因为这个函数参数均为整数,所以使用lua_tointeger
	//若其他数据类型,需使用类似的lua_to*函数
	int a1 = lua_tointeger(L,1);
	int a2 = lua_tointeger(L,2);
	int a3 = lua_tointeger(L,3);
	//打印各个参数的值
	printf("第1个参数=%d\n",a1);
	printf("第2个参数=%d\n",a2);
	printf("第3个参数=%d\n",a3);
	//将三个参数值相加并压入栈
	//使用lua_pushinteger函数将整数值压入,其他数据类型需使用类似lua_push*函数
	//若有多个返回值,按顺序压入栈
	lua_pushinteger(L,a1+a2+a3);
	// 返回值为lua函数add的返回值数量,为1.
	return 1;
}


int main()
{
    // 创建Lua状态
    lua_State* L = luaL_newstate();           
    // 打开标准库
    luaL_openlibs(L);  
	// 注册C函数C_add为lua函数add
	lua_register(L,"add",C_add);
    // 解析并执行Lua脚本字符串
	luaL_dostring(L,"
	-- add为一个用C函数C_add定义的函数
	-- 当在lua执行下面函数add时,lua语言会将参数7,2,5按顺序压入虚拟栈L,再调用C函数C_add,
	-- 后根据C函数C_add的返回值,将栈元素弹出传递给lua语言,赋值给变量a
	-- add函数功能是将三个参数进行相加
	a=add(7,2,5)
	print('a=',a) -->14
	");
	
    // 关闭Lua状态
    lua_close(L);                             
    return 0;
}

运行结果如下
在这里插入图片描述


网站公告

今日签到

点亮在社区的每一天
去签到