Lua语言入门(三)
来源:互联网 发布:tf卡数据恢复 编辑:程序博客网 时间:2024/06/05 22:47
协同程序
36、协同程序(coroutine)
4种状态:挂起(suspended)、运行(running)、死亡(dead)、正常(normal)
创建(挂起状态):
local co = coroutine.create( function() print("coroutine") end)
启动或再次启动协程(状态由挂起改为运行):
coroutine.resume(co)
coroutine在创建的时候不会自动执行。
检查协程的状态:
coroutine.status(co)
协程在运行完之后,就处于死亡状态,再也无法返回。
使用yield:
local co = coroutine.create( function() for i=1,10 do print(i) coroutine.yield() --运行到这里让该协程挂起,之后通过调用coroutine.resume恢复它的运行 end end )coroutine.resume(co) --1coroutine.resume(co) --2coroutine.resume(co) --3coroutine.resume(co) --4coroutine.resume(co) --5
当一个协程 A 唤醒另一个协程 B ,协程 A 就处于一个特殊状态,称为“正常状态”。
local co = coroutine.create( function(a, b) print("the first resume params: ", a, b); --在第一次调用resume,传递的额外参数都将视为协同程序主函数的参数; print("resume params", coroutine.yield("yield return params")) --而yield返回值就是对应resume传入的参数 return "function return" --当一个协同程序结束时,主函数返回值都将作为resume的返回值。 end )print(coroutine.resume(co, 1, 2)) --调用resume后返回的内容,第一个值为true则表示没有错误,后面所有值都是对应yield传入的值print(coroutine.resume(co, 3, 4, 5))--[[输出:the first resume params: 1 2true yield return paramsresume params 3 4 5true function return]]
36、协程应用于生产者消费者模式(最好把代码运行一下,再去理解)
function receive(prod) local status, value = coroutine.resume(prod) return valueendfunction send(x) coroutine.yield(x)endfunction producer() return coroutine.create( function() while true do local x = io.read() send(x) end end )endfunction filter(prod) return coroutine.create( function() for line = 1, math.huge do local x = receive(prod) x = string.format("%5d %s", line, x) send(x) end end )endfunction consumer(prod) while true do local x = receive(prod) io.write(x, "\n") endendp = producer()f = filter(p)consumer(f)
37、非抢先式多线程(协程):当一个协程运行时,无法从外部停止,只有协程显示的挂起(yield),才会停止。
常用数据结构
38、数组:以数字作为key的table,在lua中习惯用 1 作为数组起始,长度可变
a = {}for i =1,10 do a[i] = 0endprint(#a) --计算数组长度--直接创建并初始化数组a = {7, 6, 5, 5, 7, 8, 9, 0, 0, 5, 3}
39、多维数组,可以用类似其它语言的方式表示多维,也可以利用一维数组表示。用稀疏矩阵表示一个图,table本身就是稀疏的,可以直接表示浪费内存。
mt = {}for i=1,10 do mt[i] = {} for j=1,10 do mt[i][j] = 0 endend
遍历“稀疏矩阵”需要注意:一般使用pairs且只遍历那些非nil的元素。
pairs 和 ipairs 的区别:pairs 可以遍历表中所有的key,而ipairs 只能遍历到表中出现的一个不是整数的key
当然还有链表、队列、树、图等数据结构,这就不详细写了,这些东西和在其它语言里面是一样的
40、字符串连接:先把每个字符串存到一个数组里面,然后用table.concat连接,比用(..)连接更快更省
local a = {"A", "b", "C", "d", "E"} local s = table.concat(a)
数据持久化
41、数据文件(读取):lua常常被用来做数据存取,在lua中,所谓的数据文件就是按一定格式定义的lua文件,把该“数据文件”加载进内存,就可以直接用lua代码解析了。
local count = 0function Entry(b) count = count + 1 print("load data call : "..b[1])end--dofile("data")--data文件中就写如下的代码,这里为了简便,就直接把数据写在这里了。Entry{--注意数据文件里面的Entry必须提前定义,其实数据文件里面的Entry在调用一个名叫Entry的函数 "A", "B", "C", "D", "E"}Entry{ "f", "g", "h", "i", "j"}print("number of entries : "..count)
42、数据持久化
保存无“环”形table:
function serialize(o) if type(o) == "number" then io.write(0) elseif type(o) == "string" then io.write(string.format("%q", o)) elseif type(o) == "table" then io.write("{\n") for k,v in pairs(o) do io.write(" [") serialize(k); io.write("] = ") serialize(v) io.write(", \n") end io.write("}\n") else --其它情况 error("can not serialize a"..type(o)) endendserialize({a = 'A', b = 'Q', c = '1'})
保存有“环”形table:
43、元表:就是普通一个table,可以设置为其他表的元表,元表中可定义实现一系列的元方法
t = {}t1 = {x = "a"}setmetatable(t, t1) --把 t1 设置为 t 的元表print(getmetatable(t)) --获得 t 的元表
44、元方法:定义于元表中的那些重载的方法
算术类元方法(__add(加法),__mul(乘法),__sub(减法),__div(除法),__unm(相反数),__mod(取模),__pow(幂)):
local t = {}t.__add = function(a, b) --定义加法的元方法 return a["value"] + b["value"]endlocal obj1 = {value = 1}setmetatable(obj1, t) --local obj2 = {value = 2}--setmetatable(obj1, t)print(obj1 + obj2) --加法的时候,会检查它们其中任意一个的元表,只要有名叫__add的元方法,就会调用它定义的加法运算
关系类元方法(__eq(等于)、__lt(小于)、__le(等于)):
字符串输出元方法(__tostring):local m = {}m.__tostring = function() return "meta function"endlocal a = {}setmetatable(a, m)print(a)
保护元表:使用用户既不能看也不能修改集合的元表,定义字段 __metatable
local m = {}m.__metatable = "not your business" --保护元表local a = {}setmetatable(a, m)print(getmetatable(a)) --not your businesssetmetatable(a, m) --cannot change protected metatable
table访问的元方法:
__index元方法:当访问一个table中不存在的字段时,解释器会去查找元表中名叫__index的元方法,如果没有该方法,返回nil,否则由这个元方法提供结果。
local m = {}m.__index = function() return "index nil"endlocal a = {}setmetatable(a, m)print(a[1]) --index nil
__newindex元方法:当对一个table中不存在的索引赋值时,解释器就会查找__newindex元方法,如果元表中有该元方法,就调用它而不执行赋值。
- Lua语言入门(三)
- Lua语言入门(一)
- Lua语言入门(二)
- Lua语言入门(四)
- (三)Lua脚本语言入门
- (三)Lua脚本语言入门
- 轻量级语言Lua入门
- Lua语言基础入门
- Lua语言快速入门
- Lua语言入门2
- Lua语言基础入门
- Lua游戏开发(三)---Lua语言学习(上)
- Lua游戏开发(三)---Lua语言学习(下)
- R语言入门(三)
- Lua脚本编程:Lua语言入门
- lua语言学习三变量
- Lua 语言 15 分钟快速入门(转)
- 用C语言扩展lua模块(入门)
- TankWar 单机(JAVA版) 版本0.3 画出坦克
- Android内核开发 相关工具及源码下载汇总
- PowerDesigner,根据name自动生成commnet的脚本
- linux之简单网络命令
- 【Day14】如何用PHP替换文件的内容?
- Lua语言入门(三)
- Google疯了,竟然这样!
- HTML5的初级属性
- 和差化积&积化和差
- Spring mvc入门程序
- javaScript 之navigator
- isset()和empty()的区别
- Prime Ring Problem(HDU1016)(A)
- 国庆训练赛