lua coroutine(协程)

本文介绍了Lua协程的基本概念,包括创建、启动、挂起及状态查询等操作,并通过示例程序详细展示了协程的工作原理。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

原文地址http://www.daileinote.com/computer/lua/15

协程相关的文章网上有很多,众说纷坛,相比其他技术概念理解起来没那么直接。因为协程涉及了很多底层高并发概念,没接触过操作系统调度,C语言等底层知识根本不可能完全理解。

备注:以下我说的单进程就是指一个进程一个主线程

1.协程跟linux c里的epoll很像,都是单进程非阻塞的(也就是没有io等待,单核cpu利用率可以达到100%)

2.由于协程是单进程的所以没有存在像多线程多核cpu下的竞争关系

3.线程有抢占式和非抢占之说,而协程没有这一说,全部由你手动控制什么时候释放

4.协程的缺点是只能利用cpu的一个核,类似于node.js,想利用多核cpu得使用其他分布式技术

 

co = coroutine.create(func)

创建协程并返回

 

stat,data = coroutine.resume(co, 1)

启动协程并传入参数,当协程遇到yield时返回数据

 

stat = coroutine.status(co)

返回携程状态dead,suspend,running

 

coroutine.yield(x)

挂起协程并返回x到上面的data

 

coroutine.running()

返回正在运行的线程号

 

coroutine.wrap()

另一种启动协程的方法
co = coroutine.wrap(
    function(i)
        print(i);
    end
)
--调用方法传入参数自动启动
co(1)

 

 

以下附上一个简单的例子,目前还没有在现实项目中用到协程,以后用到了再补充

跟着下标从0-5依次读下去应该就能懂

--例子---以下程序由1-5一直循环
local newProductor

function productor()
     local i = 0
     while true do
          i = i + 1
          send(i)     --3
     end
end

function consumer()
     while true do
          local i = receive() --1
          print(i)
     end
end

function receive()
    --启动携程调用productor()
    local status, value = coroutine.resume(newProductor)   --2,5
    return value
end

function send(x)
    --挂起携程 返回到resume的地方
    coroutine.yield(x)     --4
end

-- 启动程序
newProductor = coroutine.create(productor)
consumer()    --0

 

总结

1.本文只是对lua协程做简单的介绍,如果有疑问可以给我留言
2.lua的版本为5.1,运行环境centos7 64位
3.原文地址http://www.daileinote.com/computer/lua/15

<think>我们被要求回答关于Lua协程(coroutine)的使用教程。根据提供的引用资料,我们可以构建一个清晰的教程结构。 引用[1]介绍了协程的基本概念:Lua协程是一种非抢占式的控制结构,允许函数暂停和恢复。 引用[2]列出了coroutine模块中的函数:create, yield, resume, status, running, wrap等。 引用[3]和[4]提供了创建协程的示例和协程的特性(非抢占式、显式切换、非对称协程、独立堆栈等)。 引用[5]提到了一个常见问题:协程执行完毕后需要手动置空持有对象,以避免问题。 教程结构建议: 1. 协程的基本概念 2. 创建协程coroutine.create 和 coroutine.wrap) 3. 启动/恢复协程coroutine.resume) 4. 挂起协程coroutine.yield) 5. 查看协程状态(coroutine.status) 6. 获取当前运行的协程coroutine.running) 7. 协程的注意事项和常见问题 我们将按照上述结构进行讲解,并穿插代码示例。 注意:所有行内数学表达式使用$...$,独立公式使用$$...$$(但本问题中数学公式较少,可能用不到,但需注意格式要求)。 使用中文回答。 最后生成相关问题。 根据引用资料,我们编写教程如下:</think>### Lua 协程 (coroutine) 使用教程 #### 一、协程基本概念 Lua 协程是一种**非抢占式**的轻量级线程,允许函数在执行过程中**暂停**并在稍后**恢复**执行[^1]。与操作系统线程不同: - 协程由程序**显式控制切换**(非抢占式) - 每个协程拥有独立的堆栈、局部变量和指令指针 - 协程间**共享全局变量**和其他资源[^4] ```lua print(coroutine.status(co)) --> 输出协程状态 ``` #### 二、核心函数详解 1. **创建协程** - `coroutine.create(f)`:返回协程对象(类型为`thread`) ```lua co = coroutine.create(function() print("协程启动") end) print(type(co)) --> thread ``` - `coroutine.wrap(f)`:返回可直接调用的函数 ```lua f = coroutine.wrap(function() print("Wrap方式创建") end) f() --> 直接调用执行 ``` 2. **执行控制** - `coroutine.resume(co, ...)`:启动/恢复协程 ```lua co = coroutine.create(function(a, b) print("参数:", a, b) --> 输出 10, 20 end) coroutine.resume(co, 10, 20) ``` - `coroutine.yield(...)`:挂起协程并返回值 ```lua co = coroutine.create(function() coroutine.yield("第一次暂停") return "结束" end) print(coroutine.resume(co)) --> true, "第一次暂停" print(coroutine.resume(co)) --> true, "结束" ``` 3. **状态查询** - `coroutine.status(co)`:返回状态字符串 - `"suspended"`(挂起) - `"running"`(运行中) - `"dead"`(结束) ```lua print(coroutine.status(co)) --> suspended ``` - `coroutine.running()`:返回当前运行的协程 ```lua print(coroutine.running()) --> thread: 0x7f8a3fc0 ``` #### 三、典型使用模式 1. **生产者-消费者模型** ```lua function producer() for i = 1, 3 do coroutine.yield("产品"..i) -- 挂起并传递数据 end end consumer = coroutine.wrap(producer) print(consumer()) --> 产品1 print(consumer()) --> 产品2 ``` 2. **异步任务调度** ```lua function async_task() print("开始下载...") coroutine.yield() -- 模拟网络延迟 print("处理数据...") coroutine.yield() print("保存结果") end co = coroutine.create(async_task) coroutine.resume(co) --> 开始下载... coroutine.resume(co) --> 处理数据... ``` #### 四、注意事项 1. **资源管理** 协程结束后需手动置空持有对象,避免内存泄漏[^5]: ```lua self.co = coroutine.create(function() -- ... 业务代码 ... self.co = nil -- 执行完毕后释放 end) ``` 2. **错误处理** `resume` 返回两个值:`是否成功` 和 `错误信息/返回值` ```lua success, msg = coroutine.resume(co) if not success then print("协程错误:", msg) end ``` #### 五、协程 vs 线程 | 特性 | Lua 协程 | 系统线程 | |--------------|-------------------|------------------| | 切换控制 | 显式 (`yield/resume`) | 操作系统调度 | | 并发模型 | 协作式 | 抢占式 | | 资源开销 | 极低 (KB 级) | 高 (MB 级) | | 数据共享 | 直接访问全局变量 | 需进程间通信 | > 协程特别适合:游戏AI状态机、流水线数据处理、生成器模式等场景[^4]
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值