如何在Lua中结束循环协程?
我目前正在使用Roblox(使用Lua)制作一个游戏。这是由几个小游戏组成的。在每一轮开始时,游戏中的所有玩家都被放在一个表中并传送到一个区域。协同程序就在这里发挥作用。在进展中的回合中,我希望协同程序启动。每秒钟这个协同程序检查玩家的血量是否低于零,如果是,则将其从当前玩家表中删除。
如果我描述问题不正确,那么很抱歉,但是协同程序将不会产生任何效果。我以前没有使用过协同程序,所以我可能正在尝试错误的方法来产生效果。我知道你们大多数人不熟悉Roblox,但Lua语法是相同的。
请问有人可以给我一个示例,让我知道如何结束一个循环的协同程序吗?
currentPlayers = {}
roundTime = 60
local lookForWinners = coroutine.create(function()
while coroutine.running do
wait(1)
for i, v in pairs(currentPlayers) do
if v.Character.Humanoid.Health <= 0 then
table.remove(currentPlayers, v)
end
end
end
end)
while wait() do
repeat display("Two or more players need to be in the game.", 1) until #_G.plrs > 1 --Ignore, just checks if two+ players are in game.
display("Picking a map...", 3) pickMap()
teleport(0, 500, 0)
coroutine.resume(lookForWinners)
wait(roundTime)
print("Round over")
coroutine.yield(lookForWinners)
end
我建议你跟随 Stuart 的建议使用事件; 这主要是为了提供关于协同程序的额外信息,以帮助你正确地使用它们。
将协同程序视为可以返回值的函数,但有一个特殊之处:当“普通”函数执行 return 时,它完成了,但当你从协同程序中 yield 时,它保存了自己的状态,使得 resume 可以从你 yield 的点继续执行,就好像什么也没有发生一样。请注意,你只能从协同程序中 yield,并且只能到该协同程序的 resume 执行的点(这与调用函数并从函数返回没有任何区别;控制权返回到你调用函数的点)。
此外,resume 和 yield 调用允许你向协同程序传递值并从协同程序返回(中间)值。查看这个 SO 回答 来查看如何使用这一点的示例。
仍然可以从协同程序中 return,这与从函数中返回没有任何区别,它将完成其执行。如果在那时检查协同程序的状态(coroutine.status),它应该是“已死”。
所以,回答你的问题如何结束一个循环协同程序:你可以从它中 return,你可以从它中 yield()(然后再也不 resume 它),或者你可以调用 error(),之后你可以捕获它,并在 resume 调用的结果中检查它。话虽如此,我同意 Stuart 的观点,这可能不是解决你的问题的正确方法。
- 如何将两个不同的lua文件合成一个 东西有点长 大佬请耐心看完 我是小白研究几天了都没搞定
- 如何在roblox studio中1:1导入真实世界的地形?
- 求解,lua_resume的第二次调用继续执行协程问题。
- 【上海普陀区】内向猫网络招募【Skynet游戏框架Lua后端程序员】
- SF爱好求教:如何用lua实现游戏内调用数据库函数实现账号密码注册?
- Lua实现网站后台开发
- LUA错误显式返回,社区常见的规约是怎么样的
- lua5.3下载库失败
- 请问如何实现文本框内容和某个网页搜索框内容连接,并把网页输出来的结果反馈到另外一个文本框上
- lua lanes多线程使用
- 一个kv数据库
- openresty 有没有比较轻量的 docker 镜像
- 想问一下,有大佬用过luacurl吗
- 在Lua执行过程中使用Load函数出现问题
- 为什么 neovim 里没有显示一些特殊字符?
- Lua比较两个表的值(不考虑键的顺序)
- 有个lua简单的项目,外包,有意者加微信 liuheng600456详谈,最好在成都
- 如何在 Visual Studio 2022 中运行 Lua 代码?
- addEventListener 返回 nil Lua
- Lua中获取用户配置主目录的跨平台方法
Lua是一种单线程语言。协同程序不会导致函数并行执行。
协同程序实际上只是一种可以暂停自身执行(使用
coroutine.yield)并且可以从外部恢复执行(使用coroutine.resume)的函数。没有“coroutine.running”:在任何时候只有一条“running”的指令。如果Roblox打算让您使用
wait()来跳出Lua线程,则应编写一系列循环,检查其条件,然后调用wait():local currentPlayers={} local roundTime = 60 while #_G.plrs > 1 do display("Two or more players need to be in the game.", 1) wait() end display("Picking a map...", 3) pickMap() teleport(0,500,0) for i=0,roundTime do for i, v in pairs(currentPlayers) do if v.Character.Humanoid.Health <= 0 then table.remove(currentPlayers, v) end end wait(1) end print("Round over")然而,这是不好的代码。(每当编写代码时,带有“等待”函数的循环都应该表示某些东西被错误地执行了。)您应该使用Roblox的事件处理游戏的逻辑。
与繁忙循环相比,事件具有_[许多许多]_优点;最显著的一个优点将是您的检查发生的时间是_它们正在检查的_事情发生的时间,而不是之后。