在Coroutine中"yield return 0"和"yield return null"之间有什么区别?

yum*_*gee 10 c# ienumerator yield coroutine unity-game-engine

我是新人,对" yield" 有点困惑.但最后我明白它是如何运作的WaitForSeconds

但我看不出" yield return 0"和" yield return null" 之间的区别.

他们都在等待下一帧执行吗?

对不起,我的英语不好.非常感谢你.

Pro*_*mer 22

两者yield return 0yield return null单帧的产量.最大的区别是,yield return 0分配,因为拳击与拆箱的内存0是引擎盖下发生,但yield return null没有分配内存.因此,yield return null如果您关心性能,强烈建议使用.

  • 至于性能,你正在争论毫无意义地执行一个*以(授予的,相当小的)成本增加零值*的动作.你是否只是随机地绕过你的代码插入`Thread.SpinWait`无缘无故地进入你的代码"因为它不是一个热路,所以它无所谓"?另外,这个让步的东西将在整个应用程序中完成*,因此它几乎肯定会在许多热门路径中. (4认同)
  • @YuvalItzchakov我没有做出假设,我只是利用Unity协程的一些基本知识.这里的*惯用*行为是产生'null`.这不会以任何方式出错.你假设这被视为一系列价值观,而事实并非如此.这不是Unity如何使用它的迭代器.`null`*是*最有意义的返回值,因为*point*是"没有意义的值"是正在产生的值,而`null`实际上代表那些语义*best*.肯定比一个没有任何意义的数字更好. (4认同)
  • @YuvalItzchakov迭代器块可以用来创建返回`IEnumerable <T>`的方法,但是统一协程将是`IEnumerable`类型,而不是`IEnumerable <int>`. (3认同)
  • @YuvalItzchakov您打算用该常数传达什么意思?这里的值的重点是它不是一个值,而这恰好是“ null”的语义。您还想传达什么其他语义?屈服突破完全是错误的。它无法正常运行。他需要暂停到下一帧,而不是结束协程。 (3认同)
  • @YuvalItzchakov这个问题是为了**团结**。它带有Unity标签,没有** WPF **或** WinForm **。Unity是一个游戏引擎。您不能像普通的C#应用​​程序那样进行编程,也不必关心内存分配。例如,如果您在while循环中使用“ yield return 0”进行动画处理,然后将该脚本附加到50个以上的游戏对象上,这将导致垃圾收集器发生的频率更高,从而导致游戏在某些时候冻结和解冻。这在** iOS **或** Android **上不好。您可以称其为微优化或不必要,但这不是**。 (3认同)
  • @YuvalItzchakov`0`的拳击。 (2认同)
  • @YuvalItzchakov产生时。 (2认同)
  • @YuvalItzchakov 因为协程的类型是`IEnumerable`,而不是`IEnumerable&lt;int&gt;`。当你将一个整数存储在一个 `object` 类型的变量中时,它需要被装箱。 (2认同)
  • @YuvalItzchakov 为什么你需要一个 `const` 来保存 `null`?已经 * 有一个 `null` 常量。它是`null`。为什么不必要地无缘无故分配一个新对象?我同意拥有装箱值并不是世界末日,但是通过使用被装箱的值也不会*完成*。获得更好的性能无需花费任何成本。 (2认同)
  • @Servy 感谢您回答这些问题。Yuval 认为因为只分配了 4 个字节,所以使用 `yield return 0` 是可以的。这在 Unity 中是错误的。例如,代码`while(moveObject){transform.position = ....; yield return 0;}` 将随着时间移动游戏对象。这将每秒运行 60 次,即每秒分配 240 个字节。现在,让我们将脚本附加到其他 50 多个也需要移动的游戏对象上。现在,我们在移动设备上遇到了很大的问题。我想你明白这一点。希望尤瓦尔会。快乐编码! (2认同)