找回密码
 立即注册
查看: 264|回复: 0

Unity—ECS的内存分配器原理详解

[复制链接]
发表于 2022-10-9 16:35 | 显示全部楼层 |阅读模式
ECS 为什么会高效,性能好,Entity的内存布局与分配就是非常重要的部分,今天我们一起来分析一下Unity ECS 架构里面如何来做高效的内存分配器。
欢迎加入我的学习交流群一起讨论
1: ECS 里面基本的一些概念
Unity ECS框架里面有几个重要的概念:







(Entity内存对象布局示意图)









总结一下Unity ECS的使用步骤与逻辑关系:





(Unity ECS 架构图)

2: ECS 高效的内存模型与布局

作为架构师,设计框架数据结构由为关键。特别对于游戏开发,要处理迭代成百上千个游戏物体。高效的内存模型与布局如何实现? 首先要明白怎么样布局内存才会高效。内存模型布局高效主要从两个方面来考虑:
1:内存对齐。
CPU访问不同地址的内存数据的时候,如果内存地址基于2^n 数据对齐(n根据CPU而定),访问最为高效。例如我们以16字节数据对齐,那么对象内存开始排布的时候, 从地址能整除16的内存位置开始排布。高效的内存布局,对象实例内存地址要对齐,对象实例里面的每个数据成员内存地址也要对齐。Entity的内存分配与内存布局, 在创建Entity的时候,ECS系统就会注意Entity的内存对齐,同时也会注ComponentData在Entity里面排布的内存对齐,如果没有对齐,就会空一些出来。比如16字节对齐,一个ComponentData只有14个字节,实际上排布下一个ComponentData的时候是从16字节开始排布的。
2: CPU通过地址来取到内存数据的时,数据排布一起取的速度会更快。
ECS天然就具有这种优势。所有的逻辑代码迭代都是基ComponentData的,也就是算法迭代访问处理的数据都在一起,在一个ComponentData里面。这样访问数据高效,避免了地址的来回跳转。

3: Entity内存分配器 Chunk的设计
Unity ECS 设计内存分配缓存池:
(1) 基于固定大小的Chunk来做内存缓存池。每个Chunk大小为16KB(引用来自于UnityECS 文档)
(2) 当Archetype 确定后,Entity的内存大小就确定下来,每个Chunk能分配的当前的Entity数目就能确定下来。基于Archetype创建Entity的时候,首先从内存池里面拿一个Chunk, 然后根据每个Chunk可创建Entity数目,从Chunk里面把Entity分配出去,如果chunk分配完毕,从chunk内存缓存池里面再拿一个Chunk。由于基于Archetype创建,这个Archetype的所有Entity内存大小都是一样的,等释放的时候,我们就可以基于Archetype把Entity缓存起来,重复使用之前的Entity。
对于OS而言,ECS框架基于chunk来分配和释放内存,避免了内存碎片(大小都一样)。对于ArcheType而言,又基于特定ArcheType的Entity来做内存缓存,分配和释放都非常高效。
看完Unity ECS的架构设计与内存布局,我们在其他地方做ECS架构设计(游戏服务器)就有了一个很好的参考,设计万变不离其中,大家可以好好体会一下。关注公众号,回复 ECS,有一节我讲解的 Unity ECS开发的课程,帮助更进一步掌握了解Unity ECS。

本帖子中包含更多资源

您需要 登录 才可以下载或查看,没有账号?立即注册

×
懒得打字嘛,点击右侧快捷回复 【右侧内容,后台自定义】
您需要登录后才可以回帖 登录 | 立即注册

本版积分规则

小黑屋|手机版|Unity开发者联盟 ( 粤ICP备20003399号 )

GMT+8, 2024-9-21 22:50 , Processed in 0.092489 second(s), 26 queries .

Powered by Discuz! X3.5 Licensed

© 2001-2024 Discuz! Team.

快速回复 返回顶部 返回列表