3

我刚开始学习 Unity 脚本,我很难理解为什么有些人更喜欢协程而不是状态机。

我确实理解代码对于某些程序员来说可能更具可读性,但我不明白为什么有些人说使用协程对性能更可取。

我在 Unity 中使用 C#,据我了解,C# 编译器将 IEnumerator 转换为 state machine

所以也许我在这里遗漏了一些东西。使用协程而不是 FSM 循环来处理行为和状态是否会更好地提高运行时性能?如果是,为什么?

4

3 回答 3

7

在某些情况下使用协程会更快,因为您可以方便地安排 Unity 以特定间隔执行操作,而不是每帧都执行操作,从而节省处理时间。真正节省时间的是调度,而不是协程。

以您在 Unity 文档中突出显示的示例(在其他答案中的评论中)为例,其中说:

使用协程。Update 调用的问题在于它们每帧都会发生。很可能只能每 5 秒检查一次与玩家的距离。这将节省大量的处理能力。

这就是说,使用的协程WaitForSeconds( 5f )会比每帧检查距离更快。这并不意味着这样做一定比拥有自己的Update逻辑(每五秒检查一次距离)更快。

Update话虽如此,如果协程方法仍然比基于每五秒检查一次的逻辑更快(尽管没有那么明显),我不会感到惊讶,因为您仍然可以节省每帧检查当前帧的时间你的游戏代码。是的,在 Unity 的引擎循环中的某个地方,这个时间检查仍在进行,并用于确定是否进入下一个协程步骤,但它可能已经高度优化并且无论如何都会发生,所以协程没有添加太多额外的时间检查逻辑作为Update基于 - 的方法。

顺便说一句,有关 Unity 可能如何实现协程的一个很好的概述,请参阅这篇文。

于 2013-02-03T19:24:35.163 回答
2

你必须小心你使用协程的目的。它们非常适合您不想挂起游戏的长时间运行的操作。

但是,您必须非常小心在协程中产生的频率。每次屈服时,协程恢复需要一些时间(多帧)。如果你产生太多,你的协程将比它需要的处理慢。例如,我正在研究寻路系统。我正在使用协程在运行寻路算法时定期产生。这导致寻路代码花费的时间比应有的要长得多。我发现在 Update 中执行此操作要快得多。

协程非常适合执行长时间运行的异步任务,例如 Web 请求或在后台下载某些内容等。我不知道我是否会建议将协程用于您的主游戏处理循环。(尤其是输入)

于 2015-03-01T17:17:43.590 回答
1

我不认为有一个普遍的答案。这在很大程度上取决于您在代码中所做的事情。写得不好的协程可能比写得好的 FSM 慢,反之亦然。我想说代码的可读性和可理解性总是胜过潜在的(并且在这种状态下是无形的)性能提升。如果您遇到特定的性能问题,请在遇到它时解决它。所以我建议您使用对您和您的团队最直观的方法。

于 2013-02-01T08:35:47.510 回答