`
lua
  • 浏览: 76398 次
  • 性别: Icon_minigender_1
  • 来自: 大连
文章分类
社区版块
存档分类
最新评论

Lua的Iterator以及函数心得

阅读更多

http://sunxiunan.com/?p=1249

 

local tbl = {"one", "two", "three", ‘five’}
local count = #tbl
local inc = 0

function Iter(tableinput)
return function()
if inc > count then
return
end
inc = inc + 1
return tableinput[inc], inc
end
end

for elem, index in Iter(tbl) do
print(elem)
if index > 2 then
inc = 0
end
end

如果运行一下的话,不出意外一定会死循环。如果把函数Iter改一下就是我们常见的generic for了。

function Iter(tableinput)
local count2 = #tbl
local inc2 = 0

return function()
if inc2 > count2 then
return
end
inc2 = inc2 + 1
return tableinput[inc2], inc2
end
end

跟踪一下运行也可以发现,count2以及inc2这两行在Iter被for调用的时候,只会第一次运行而且只运行一次。接下来的调用中只会从return function这里开始。如果返回nil,那么for就停止循环。

我比较好奇的是,对于Iter在for循环的时候,很显然是保持了一个内部的堆栈不变,也就是说inc2和count2类似于c语言的static内部变量。但是学的还是一知半解,不知道如何dump出此时的堆栈状态。

关于函数对于局部变量,好像是会在栈上做一个缓存,看下面代码

stringb = "bbbbbbbbbbbbbbb"
do
local internalA = "print for first time"
function printStrA()
print(internalA)
end
function printStrB()
print(stringb)
end
end

do
local internalA = "!!!!!!!!!!!!!!!!!!!!"
stringb = "cccccccccccccccc"
printStrA()
printStrB()
end

internalA = "!!!!2222222222222"
printStrA()
stringb = "ddddddddddddddddddd"
printStrB()

当我们运行这段代码,可以发现

print for first time
cccccccccccccccc
print for first time
ddddddddddddddddddd

也就是对于printStrA,每次调用的结果都是一样的,而printStrB的结果会根据全局变量stringb的不同而不同。这一点值得以后的研究。

关于闭包(closures),PIL上有一个很有意思的例子,我做了一些扩展。

local x = function ()
    local i = 0
    print "aaa"
    local function x2()
        i = i + 1
        print "bbb"
        return i
    end
    return x2 — 这个地方不能是return x2(),否则返回的就是值而不是函数
end

x()
print "======="
x()
print "======="

local c = x()
print "======="
print(c())
print "======="
print(c())
print "======="
print(c())
print "======="

local c = x()
print "======="
print(c())

结果会是什么呢?

首先,很有意思的一点是,对于返回正确函数尾调用,一种情况下,return function()后面的代码不会运行,就是说当x()时,以及当local c=x()的时候。

我们如果想达到计数器的效果,一定要用local c=x(),然后反复调用c(),而不是调用x()。原因就是c实际上指向了x返回的匿名函数,这样每次运行c,实际上运行的就是那个匿名函数。另外一个有趣的结论是,对于返回正确尾调用的函数,尾调用实际上还没有运行。

运行的结果就是下面这样,你猜对了么?

aaa
=======
aaa
=======
aaa
=======
bbb
1
=======
bbb
2
=======
bbb
3
=======
aaa
=======
bbb
1

关于尾调用, return g(x)是尾调用,而return (g(x))就不是,原因是return (Fun()) — This expression is a single function call surrounded in parentheses, which is different than the required single function call (the parentheses adjust Fun to one return value).

0
0
分享到:
评论

相关推荐

    lua调用C++函数

    4. **C++函数处理Lua栈**:Lua的所有数据都存储在一个虚拟栈上,C++函数需要通过`lua_gettop`检查栈顶元素,`lua_pushinteger`、`lua_pushstring`等函数将数据压入栈,以及`lua_to*`系列函数将栈上的值转换为C++类型...

    Lua调用C++函数实现

    使用 `luaL_newstate` 创建 Lua 状态机,`luaL_openlibs` 打开标准库,然后使用 `lua_register` 或 `lua_pushcfunction` 注册 C++ 函数到 Lua 环境中。 2. **C++ 函数签名**: 当注册 C++ 函数时,必须考虑到 Lua ...

    Lua编程事例:调用Lua有参函数

    `lua_pushnumber`将C++的数值转换为Lua的数值类型并压栈,`lua_pcall`执行函数并传递参数个数(2),期望返回值个数(0)以及错误处理方法。 注意,每次调用Lua函数后,都需要检查错误状态,并清理栈,以避免内存...

    lua调用c函数库的demo

    lua调用c函数库的demo 其中实现了对一个 数组的管理。 注意lua参数与c函数的对应, 如:b=lua_dllb.getarray(a,1) static int getarray(lua_State* L) { NumArray * a=(NumArray*)lua_touserdata(L,1); //对应lua...

    Lua 类的继承与函数override

    接下来,我们将深入探讨 Lua 中的类、继承以及函数重写(override)。 首先,让我们理解 Lua 中的“类”。在 Lua 中,你可以创建一个表来代表类,这个表包含了对象的所有属性和方法。例如: ```lua Person = { ...

    Lua的最基本使用 C++与lua的互相调用

    在本文中,我们将深入探讨如何在C++程序中集成Lua,实现C++调用Lua函数以及Lua调用C++函数。 一、C++调用Lua函数 1. 配置环境:首先,你需要在C++项目中包含Lua库。确保已经下载并正确安装了Lua,并将其头文件和库...

    串口屏LUA例程-常用的回调函数使用说明V1.0.pdf

    本文档主要介绍了在大彩物联型串口屏上使用LUA脚本进行编程时,涉及的一些核心概念是关于回调函数的使用方法以及编程注意事项。大彩LUA脚本API中提供了一系列的回调函数,这些函数在特定事件发生时被自动调用,可以...

    Lua的使用入门之在C++程序中调用lua函数1

    要从C++中调用Lua函数,首先需要使用`lua_getglobal()`获取全局函数引用,然后通过`lua_pcall()`执行该函数。假设`move`函数在全局环境中,调用方式如下: ```cpp lua_getglobal(L, "move"); // 获取move函数 if...

    Lua中调用C函数

    在Linux底下,从Lua中调用C函数的一个简单例子。

    lua参考手册和lua常用函数

    这份资源包含“lua参考手册”和“lua常用函数”的详细介绍,是学习和理解Lua语法及函数用法的重要参考资料。 《lua参考手册》通常会涵盖以下内容: 1. **基础语法**:包括变量定义(全局与局部)、数据类型(如nil...

    LuaAction C++访问LUA函数

    本文将详细阐述如何利用LuaAction来实现这一功能,以及它所支持的特性。 首先,LuaAction的核心特性之一是能够访问Lua环境中的包或表内的函数。在Lua中,包和表是其主要的数据结构,它们可以用来组织和存储各种数据...

    Lua UnPack函数用法实例

    在Lua编程语言中,unpack函数是一个非常实用且高效的工具,它主要用于从数组类型的table中解包元素。在本文中,我们将详细介绍unpack函数的用法,包括它的基本功能和如何通过实例来掌握它的使用技巧。 首先,让我们...

    C\C++中调用Lua函数的接口封装

    它提供了一系列的函数,如`luaL_newstate`用于创建一个新的Lua环境,`luaL_openlibs`打开默认的库,以及`luaL_loadbuffer`或`luaL_dofile`用于加载和运行Lua脚本。 2. **进栈和出栈**: - **进栈**:将C/C++的数据...

    tolua++ 版helloworld (lua脚本调用C++类的成员函数方法)

    关于tolua++的资料太少,这个通过实例让你知道如何通过tolua++和C++交互,简单明了。 通过5个文件来演示这个tolua++版 hello world hello.lua ,hello.h ,hello.pkg ,...这个程序实现了脚本调用C++类的成员函数方法

    LUA5.4动态链接库,支持中文函数,适用于Nlua

    LUA5.4放宽了这一限制,允许使用中文字符作为函数名,极大地拓宽了LUA在全球范围内的使用场景,特别是在中文编程环境中,使得代码更易于理解和阅读。 在提供的压缩包中,luadll文件可能包含了x86和x64两种架构的...

    windows 下使用 Lua 绘制正弦函数

    Programming in lua 艺一书中第6章再论函数,写了一个lua 实现绘制正弦函数的例子,但最后却说,“要想让这个例子正确的运行,你必须调整你的终端类型和代码中的控制符一致”,网上查了一下,意思就是这段代码linux...

    cocos2dx在LuaStudio中基本库函数配置文件

    其中配置包括了cocos2dx 2.0.4和cocos2dx2.1.3在lua中所有函数,类,类的成员变量和方法以及相关枚举定义 使用方法: 1.打开本目录下LuaKeywords.config,将里面内容复制到LuaStudio的自定义函数配置中 2.拷贝cocos...

    delphi7与lua相互调用的例子

    例如,可以导入`lua_pcall`来执行Lua脚本,`lua_gettop`获取 Lua 栈顶的元素数量,以及`lua_pushstring`和`lua_tostring`来传递和转换字符串等数据类型。这些函数的使用方式与C语言中的API保持一致。 在Delphi项目...

    C# lua库 支持中文函数名中文变量

    LuaInterface是C#中一个常用的Lua绑定库,它提供了在C#代码中调用Lua函数,以及在Lua脚本中访问C#对象的能力。在Lua 5.1版本中,这个库已经实现了对中文函数名和变量名的支持。这意味着在编写Lua脚本时,你可以使用...

    易语言LUA支持库1.0#0版(第三方)

    LUA脚本支持库 (1.0#0版)是对LUA5.1.4的封装,包含了 “LUA”数据类型,LUA函数操作函数等。下面对易语言中使用LUA做一个简单的介绍。LUAC函数操作(命令分类)。这是一组全局函数,当您在您的应用程序中实现一个...

Global site tag (gtag.js) - Google Analytics