unity 下一帧执行_理解Unity中的优化(三):协程(Coroutines)
Coroutines:
Coroutines与其他脚本代码的执行方式不同。在性能分析中,大多数的脚本代码只会在Unity的生命周期方法下出现一次。但是协程总是会在两个地方出现。
在性能分析中,Coroutines中所有从协程开始到第一个yield中的代码,都会出现在协程出现的地方。通常,它会在StartCoroutine的方法中出现。由Unity回调产生的Coroutines(例如Start回调返回一个IEnumerator),首先会出现在各自的回调中。
协程中剩余的代码(从第一次恢复到完成执行),会出现在Unity的主循环,DelayedCallManager方法中。
要理解为什么出现这种情况,就需要理解协程实际上是怎么执行的:
协程运行时,C#编译器会自动生成一个类。这个类会在多个调用中,追踪Coroutine的状态。对于局部变量,由于协程中的局部变量在yield后也必须存在,所以这些局部变量会被封装到生成类里面。在协程执行期间,这些变量就会在托管堆中持续存在。这个对象也会追踪协程的内部状态:它会记录在yield之后,协程会在什么时候继续执行。
正因为如此,启动一个coroutine的内存开销等于一个固定的开销成本加上它的局部变量的开销。
开始调用一个协程的代码,在协程满足yield条件时,Unity会通过DelayedCallManager再次调用它们。因为协程有时候是被另一个协程调用的,这时候它们的开销就是上述两个被拆分的开销。
在上述的截图中,我们可以看到,DelayedCallManager执行执行了几个协程,PopulateCharacters, AsyncLoad 和LoadDatabase。
在可能的情况下,最好在单个协程中执行一系列的操作,虽然在代码的清晰度和可维护方面,嵌套调用的协程比较好,但由于需要追踪对象,嵌套调用将会花费更高的内存。
如果,一个协程每帧都会被执行, 并且在长时间的操作中没有yield语句。那么最好把里面的代码放到Update或者LateUpdate中。
当一个对象被设置成disable时,协程不会停止,只有当对象被destroy时,才会停止。就是说,disable一个对象时,协程仍然在运行,需要的话,可以在协程中enable这个对象。调用Destroy(this)会立即触发OnDisable回调,同时,协程也会被停止。最后,在最后一帧会调用OnDestroy方法。
协程不是线程,记住这个很重要。协程中的操作依旧运行在主线程上。如果在优化的目标是减少CPU在主线程上话费的时间,那么在协程中避免出现一些阻塞的操作跟在其他代码中避免出现一样重要。
当然,当我们需要执行一些例如Http传输、Asset加载或者文件I/O操作这类长时间的异步操作时,最好使用协程。
本文内容来自Unity官方文档:
Unity - Manual: Coroutinesdocs.unity3d.com
作者水平有限,如有错误请多加指正。
unity 下一帧执行_理解Unity中的优化(三):协程(Coroutines)相关推荐
- unity 下一帧执行_Unity中的Havok Physics物理引擎
在GDC 2019上,我们宣布将Havok Physics作为预览版资源包加入到Unity资源包管理器,这意味着所有Unity开发者都可以使用这款知名的物理引擎.在当今主机平台中,Havok Phys ...
- unity怪物攻击玩家减血_利用Unity协程实现一个简单的怪物寻路与跟随AI
利用Unity协程实现一个简单的怪物寻路与跟随AI,通过分析怪物行为与逻辑,实现简单的平面怪物寻路与跟随效果. 分析 对于游戏中怪物的行为,简单归纳为如下几部分: 怪物在预设范围内随机移动. 玩家走入 ...
- unity ui 补间动画_杭州Unity游戏开发培训内容有哪些?学习路线是如何规划的?...
现在Unity游戏开发行业越来越受到欢迎,但是想要找到适合自己的课程和学习方法却有些困难.很多刚开始接触Unity游戏开发且没有基础的同学,不知道该从哪里开始学,也不知道要学习什么内容.该怎么开始Un ...
- unity代码更换ui图片_关于Unity UI的动静图集分离,你需要了解这些!
这是第101篇UWA技术知识分享的推送!(此处应有掌声)随着大家在UWA平台上的发言愈加活跃,我们也源源不断地收到了许多技术大咖的热心回复和真知灼见. UWA 问答社区:answer.uwa4d.co ...
- go 怎么等待所有的协程完成_理解真实世界中 Go 的并发 BUG
点击上方蓝色"Go语言中文网"关注,回复「电子书」领全套Go资料 有几个学生研究归纳了go编程中的并发bugs,发表了一篇(英文)论文:<Understanding Real ...
- javascript 符号_理解JavaScript中“ =”符号的直观指南
javascript 符号 by Kevin Kononenko 凯文·科诺年科(Kevin Kononenko) 理解JavaScript中" ="符号的直观指南 (A Visu ...
- js原型和原型链_理解JS中的原型和原型链
导读:JavaScript中(JS)的原型和原型链是web前端开发面试中经常被问到的问题:同时,如果我们能很好的理解JS中的原型和原型链,对于控制台输出的很多信息我们也能更好的理解,而原型链也是实现继 ...
- java的弱引用_理解Java中的弱引用(Weak Reference)
本篇文章尝试从What.Why.How这三个角度来探索Java中的弱引用,理解Java中弱引用的定义.基本使用场景和使用方法.由于个人水平有限,叙述中难免存在不准确或是不清晰的地方,希望大家可以指出, ...
- python中元组_理解python中的元组
理解 python 中的元组 引言 在 Python 中元组是这样的: 元组是是这样一种数据结构:不变的或者不可改变的(简单来说不能重新赋值) .元素的有序序列.因为元组是 不变的,所以他的数值是不能 ...
最新文章
- 开源用于寻找系外行星的代码
- 机械转嵌入式还是java,机械硕士转嵌入式后悔吗?
- TreeView复选框选择逻辑判断
- 提交代码前问自己七个问题!
- MySQL高级 - 查询缓存 - 开启查询缓存
- Java overview JVM
- 实战Java内存泄漏问题分析 -- hazelcast2.0.3使用时内存泄漏 -- 2
- 网络安全案例研究:“神秘”的加密指纹
- 吉士丁与新潮传媒达成亿级战略合作,打造国产奶酪新势力
- [No0000F9]C# 运算符重载
- C# C++ 共享内存 结构体读写 结构体中嵌套结构体 结构体中带string Char*的处理方式
- 用户一键登陆,如何实现?了解一下!
- LSR:用于文档关系抽取的潜在图结构迭代优化推理方法
- 产品经理如何建立和促进心理安全
- 清者自清!国际泳联为孙杨“药检风波”盖棺定论
- AD20使用之 手动创建封装
- 免费送机械键盘,不是粉丝的绕道!!!
- ADaM---Analyis Data Model implementation Guide V1.3
- mac版本的xshell远程ssh工具
- linux终端窗口适应屏幕,自动调整2个窗口占用屏幕一半的方法
热门文章
- Tomcat5配置mysql4数据源
- C#实现RSA加密解密
- Go 语言范围(Range)
- ElasticSearch入门 :Windows下安装ElasticSearch
- Spring MVC之@RequestMapping 详解
- SgmlReader使用方法
- 无法加载 DLL“oramts.dll”: 找不到指定的模块。 (异常来自 HRESULT:0x8007007E)
- 调焦后焦实现不同距离成像_“物镜校正环调节”对显微成像的影响
- PHP获取数组最后一个值的2种方法
- 第八章 流量复制/AB测试/协程