c调用 lua 栈操作
转自https://www.cnblogs.com/ringofthec/archive/2010/10/22/lua.html
打算记录一些lua_api, 可能会觉得lua文档中已经说的很清楚了, 但是我将用自己的方式, 记录下我认为重要的东西, 先约定一下api说明的格式
编号. api作用简述
api函数原型
api操作说明
返回值说明
对栈的影响
注意事项
1. 建一个新表
void lua_createtable (lua_State *L, int narr, int nrec)
创建一个新的table, 并把它放在栈顶. narr和nrec分别指定该table的array部分和hash部分的预分配元素数量
无返回值
栈高度+1, 栈顶元素是新table
#define lua_newtable(L) lua_createtable(L, 0, 0) 常用这个
2. 取表中的元素
https://www.cnblogs.com/chuanwei-zhang/p/4077247.html
void lua_gettable (lua_State *L, int index);
把t[k] 值压入堆栈,这里的 t 是指有效索引 index 指向的值,而 k 则是栈顶放的值。这个函数会弹出堆栈上的 key,把结果放在栈上相同位置。
void lua_getfield (lua_State *L, int index, const char *k)
操作: arr = Stack[index] // arr肯定是表
Stack.push( arr[k] )
取表中键为k的元素, 这里的表是由index指向的栈上的一个表
无返回值
栈高度+1, 栈顶元素是(Stack[index])[k]
注意, 该操作将触发 __index 元方法
3. 给表中的元素赋值
void lua_setfield (lua_State *L, int index, const char *k)
操作: arr = Stack[index]
arr[k] = Stack.top()
Stack.pop()
给表中键为k的元素赋值value(value就是栈顶元素), 这里的表是由index指向的栈上的一个表
无返回值
栈高度-1, 被弹出的是value
注意, 该操作将触发 __newindex 元方法
4. 取表元素 和 表元素赋值
void lua_gettable (lua_State *L, int index)
操作: ele = Stack[index]
key = Stack.top()
Stack.pop()
value = ele[key]
Stack.push(value)
根据index指定取到相应的表; 取栈顶元素为key, 并弹出栈; 获取表中key的值压入栈顶.
无返回值
栈高度不变, 但是发生了一次弹出和压入的操作, 弹出的是key, 压入的是value
注意, 该操作将触发 __index 元方法
void lua_settable (lua_State *L, int index)
操作: ele = Stack[index]
value = Stack.top()
Stack.pop()
key = Stack.top()
Stack.pop()
ele[key] = value
根据index指定取到相应的表; 取栈顶元素做value, 弹出之; 再取当前栈顶元素做key, 亦弹出之; 然后将表的键为key的元素赋值为value
无返回值
栈高度-2, 第一次弹出value, 第二次弹出key
注意, 该操作将触发 __newindex 元方法
5. 对table的一些操作[不引发原方法]
void lua_rawget (lua_State *L, int index)
和lua_gettable操作一样
但是不触发相应的元方法
void lua_rawgeti(lua_State *L, int index, int n)
操作: ele = Stack[index]
value = ele[n]
Stack.push(value)
无返回值
栈+1, 栈顶新增元素就是 value
不触发相应的元方法
void lua_rawset (lua_State *L, int index)
和lua_settable操作一样
但是不触发相应的原方法
void lua_rawseti (lua_State *L, int index, int n)
操作: ele = Stack[index]
value = Stack.top()
Stack.pop()
ele[n] = value
无返回值
栈-1, 栈顶将value弹出
不触发相应的元方法
6. 复制栈上元素并压入栈
void lua_pushvalue (lua_State *L, int index)
操作: value = Stack[index]
Stack.push(value)
无返回值
栈+1
7. 创建一个元表
int luaL_newmetatable (lua_State *L, const char *tname)
操作: 1. 在注册表中查找tname, 如果已经注册, 就返回0, 否者继续, 并平栈
lua_getfield(L, LUA_REGISTRYINDEX, tname)
if (!lua_isnil(L, -1))
return 0;
lua_pop(L, 1);
2. 创建一个表, 并注册, 返回1
lua_newtable(L)
lua_pushvalue(L, -1)
lua_setfield(L, LUA_REGISTRYINDEX, tname)
return 1
有返回值
栈+1, 栈顶元素是在注册表中注册过的新表
8. 创建C值
void *lua_newuserdata (lua_State *L, size_t size)
该函数分配一块由size指定大小的内存块, 并放在栈顶
返回值是新分配的块的地址
栈+1, 栈顶是userdata
userdata用来在lua中表示c中的值. 一个完整的userdata有自己的元表, 在垃圾回收时, 可以调用它的元表的__gc方法
9. 注册c函数到lua中, 其实没有这回事, lua中只有c闭包
void lua_pushcclosure (lua_State *L, lua_CFunction fn, int n)
向栈上压一个C闭包
当一个c函数被创建时, 可以绑定几个值在它上面, 从而形成一个闭包. 在任何时刻调用这个c函数时, 都可以访问这几个绑定值.
绑定的方法: 先一次压入要绑定的n个值到栈上, 然后调用lua_pushcclosure(L, fn, n)这样就形成的一个c闭包
无返回值
栈 –(n - 1) , 一共弹出n个元素(及那些绑定的值), 压入一个cclosure
#define lua_pushcfunction(L, f) lua_pushcclosure(L, f, 0)
#define lua_register(L, n, f) (lua_pushcfunction(L, f), lua_setglobal(L, n))
没有返回值
栈不变化
这个是比较常用的, 以n为lua中的key压入一个0个绑定值的cclosure.
c调用 lua 栈操作的更多相关文章
- lua和C++交互的lua栈操作——以LuaTinker为例
一. -- C++类注册函数(LuaTinker) 的lua栈操作: -- lua栈内容(执行到pop语句) 栈地址 <--执行语句 space_name[name] = t1 -- (2b8) ...
- Lua的栈及基本栈操作
Lua的栈及基本栈操作 https://blog.csdn.net/mydriverc2/article/details/51134737 https://blog.csdn.net/mydriver ...
- Lua和C++交互 学习记录之二:栈操作
主要内容转载自:子龙山人博客(强烈建议去子龙山人博客完全学习一遍) 部分内容查阅自:<Lua 5.3 参考手册>中文版 译者 云风 制作 Kavcc vs2013+lua-5.3.3 1 ...
- VC和VS调用Lua设置以及Lua C API使用。
通过c++调用lua 脚本, 环境VC++6.0 lua sdk 5.1.4 在调用前先认识几个函数.1.调用lua_open()将创建一个指向Lua解释器的指针.2. luaL_ope ...
- 简述C/C++调用lua中实现的自定义函数
1.首先说下目的,为什么要这么做 ? 正式项目中,希望主程序尽量不做修改,于是使用C/C++完成功能的主干(即不需要经常变动的部分)用lua这类轻量级的解释性语言实现一些存在不确定性的功能逻辑:所以, ...
- ulua c#调用lua中模拟的类成员函数
项目使用ulua,我神烦这个东西.lua单纯在lua环境使用还好,一旦要跟外界交互,各种月经不调就来了.要记住贼多的细节,你才能稍微处理好.一个破栈,pop来push去,位置一会在-1,一会在-3,2 ...
- 通过lua栈了解lua与c的交互
lua是如何执行的 其中分析.执行部分都是c语言实现的. lua与c的关系 lua的虚拟机是用c语言实现的,换句话说一段lua指令最终在执行时都是当作c语言来执行的,lua的global表,函数调用栈 ...
- Lua与C++交互初探之C++调用Lua
Lua与C++交互初探之C++调用Lua 自从学习了lua这个脚本语言之后,无时不想着将他与c/c++联系起来,看看他真正的威力.奈何水平有限,网上找的代码无论怎样都无法运行成功.我知道是我少了某一步 ...
- Step By Step(C调用Lua)
Step By Step(C调用Lua) 1. 基础: Lua的一项重要用途就是作为一种配置语言.现在从一个简单的示例开始吧. --这里是用Lua代码定义的窗口大小的配置信息 wid ...
随机推荐
- UNITY的UI之Pivot与Anchor区别
Pivot Rotations, size, and scale modifications occur around the pivot so the position of the pivot a ...
- 英文单词cipher 和password的区别,用法有什么不同,
['saɪfə(r)] cipher 指一套密码系统,比如电影<风声>中破译的那个系统叫cipher:password 则指进入的指令,比如你的qq密码,电脑密码等叫password.总之 ...
- cs231n(一)
1.Nearest Neighbor Classifier 计算未分类数据(图片)与已标记类别的训练数据(training set)的距离(L1,L2等距离),然后返回与训练数据(图片)最小距离的图片 ...
- 电脑破解wifi密码(至少连过1次的才可以)
电脑破解wifi密码(至少连过1次的才可以) 连过的wifi密码忘记了怎么办? 只要你电脑连过的都能破解. cmd输入以下内容查看电脑连接过的wifi名字. netsh wlan show profi ...
- Debian/Linux系统安全配置教程
禁止root SSH登陆 配置SSH Key 配置iptables 当我们安装完Linux系统作为服务器后,总有一系列的安全配置需要进行.特别是当你的服务器Ip是对外网开放的话.全世界有很多不怀好意的 ...
- mybatis思维导图(二)
写在前面 上一篇文章写了mybatis的基本原理和配置文件的基本使用,这一篇写mybatis的使用,主要包括与sping集成.动态sql.还有mapper的xml文件一下复杂配置等.值得注意的是,导图 ...
- 白盒测试实践-任务进度-Day01
12-05 任务安排 小组成员 华同学.郭同学.覃同学.刘同学.穆同学.沈同学 任务划分 任务1:依据白盒测试方法设计测试用例 说明:我们小组就不使用测试管理工具了,直接用excel文件的形式记录,具 ...
- 两款JSON类库Jackson与JSON-lib的性能对比(新增第三款测试)
本篇文章主要介绍了"两款JSON类库Jackson与JSON-lib的性能对比(新增第三款测试)",主要涉及到两款JSON类库Jackson与JSON-lib的性能对比(新增第三款 ...
- Logstash 算术运算操作
需求:input为json,output为ES,需使用filter提取json中的某个字段,并执行加法.加法.乘法等算法操作 思路:mutate过滤器+ruby过滤器实现 避坑:根据ES及Logsta ...
- js代码定义类代码的领悟
var Class = { create: function() { return function() { this.initialize.apply(this, argumen ...