lua C语言api学习4 编写C模块

1 简介

在上节学习了如何编写可以在lua语言中调用的C函数,但是要想使用这个C函数,我们必须在程序中使用lua_register函数进行注册,再重新进行编译.对于另外一种情况就是程序已经编译好,如lua解释器等,要想使用如前面的C_add函数,必须重新修改lua.c的源码重新编译比较麻烦,可以采用这个函数写成C模块方式并编译成动态链接库模式,使用时再采用lua加载模块方式载入。

2 C模块代码

编写C模块代码,并声明一个mylib数组,定义一个luaopen_mylib打开函数,具体如下.

c 复制代码
//06C模块代码.c
//编译为mylib.dll可以在lua动态载入
#include <stdio.h>
#include <stdlib.h>

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


// 定义C函数,与上一节相同
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;
}

//声明一个数组,数组元素类型为luaL_Reg,字段分布为{注册函数名字符串,函数指针}
//最后一项必须为{NULL,NULL}	
static const struct luaL_Reg mylib[]={
	{"add",C_add},
	{NULL,NULL}	
};

// 定义C模块打开函数
int luaopen_mylib(lua_State *L){
	// 对函数 lual_newlib的调用会新创建一个表,
	// 并使用由数组 mylib指定的"函数名-函数指针"填充这个新创建的表。
	// 当lual_newlib返回时,它把这个新创建的表留在了栈中,在表中它打开了这个库。
	luaL_newlib(L,mylib);
	//返回1,表示将这个表返回给Lua。
	return 1;
}

3 编译C模块

使用需将上诉C模块代码编译为mylib.dll才能使用,在批处理界面输入编译指令如下

c 复制代码
::编译为动态链接库mylib.dll,编译需用到lua.dll
tcc -shared -rdynamic -I %lua_src% lua.dll 06C模块代码.c  -o mylib.dll

4 编写调用C程序

对上一节程序修改如下,在lua语言中动态加载mylib.dll并使用。

c 复制代码
//07lua中调用C模块
#include <stdio.h>
#include <stdlib.h>

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




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

    // 解析并执行Lua脚本字符串
	luaL_dostring(L,"
	-- 使用require函数载入C模块mylib
	mylib=require('mylib')
	-- 调用mylib库中的add函数
	a=mylib.add(7,2,5)
	print('a=',a) -->14
	");
	
    // 关闭Lua线程
    lua_close(L);                             
    return 0;
}

运行结果如下

5 在lua解释器中使用C模块

在上面例子中C模块是在lua动态载入,也可以在已编译好的程序中载入该c模块。如我们常用的lua解释器。

先创建一个lua解释器,在批处理窗口输入编译并运行lua解释器

c 复制代码
::编译lua解释器
tcc -I %lua_src% lua.def %lua_src%\lua.c -o lua.exe
::运行lua解释器
lua

输入下面lua代码即可调用C模块函数

lua 复制代码
-- 使用require函数载入C模块mylib
mylib=require('mylib')
-- 调用mylib库中的add函数
a=mylib.add(7,2,5)
print('a=',a) -->14

运行结果如下。

相关推荐
虾球xz5 分钟前
游戏引擎学习第161天
人工智能·学习·游戏引擎
小呀小萝卜儿1 小时前
2025-03-15 学习记录--C/C++-C语言 %.0f的使用和round函数(实现四舍五入)
c语言·学习
knightkkzboy2 小时前
《C语言中的“神秘符号”:转义字符的奥秘》
c语言·开发语言
庭前云落2 小时前
从零开始的 Kafka 学习(三)| 创建主题
分布式·学习·kafka
2401_878454533 小时前
es6初步学习
学习·ajax·es6
誓约酱4 小时前
linux 下消息队列
linux·运维·服务器·c语言·c++
Three~stone4 小时前
Vue学习笔记集--六大指令
vue.js·笔记·学习
电子艾号哲5 小时前
STC89C52单片机学习——第20节: [8-2]串口向电脑发送数据&电脑通过串口控制LED
单片机·学习·电脑
张胤尘5 小时前
C/C++ | 每日一练 (6)
c语言·c++·面试