Unity 的 DOTS(Data-Oriented Technology Stack)是面向性能极致优化的一种架构范式,其底层结构设计并非偶然,而是深思熟虑的结果。本篇文章将从开发者最熟悉的入口——MonoBehaviour 脚本 + Baker 入手,逐步剖析 DOTS 中 Entity 是如何生成与组织的,并深入理解其底层架构:Archetype、Chunk、Entity 的设计逻辑和动机。


一、从 MonoBehaviour + Baker 生成 Entity 说起

在 Unity DOTS 中,我们通过 Authoring + Baker 的方式将传统的 GameObject 转换为 Entity。一个常见的写法如下:

public class MonsterAuthoring : MonoBehaviour
{
public int MonsterType; class Baker : Baker<MonsterAuthoring>
{
public override void Bake(MonsterAuthoring authoring)
{
var entity = GetEntity(TransformUsageFlags.Dynamic);
AddComponent(entity, new Health { Value = 100 });
AddComponent(entity, new Translation { Value = float3.zero });
AddSharedComponent(entity, new MonsterType { TypeId = authoring.MonsterType });
}
}
}

表面上看,我们只是在添加组件。然而在背后,Unity DOTS 会根据这些组件自动为这个 Entity 创建归属结构——Archetype,并为其分配内存空间——Chunk。


二、Entity 是什么?

Entity 是 DOTS 中最基本的单位,但本身并不存储任何数据,它只是一个引用句柄:

public struct Entity
{
public int Index; // 在内部数组中的位置
public int Version; // 生命周期安全检测用
}

Entity 代表的是一个“ID”,它的数据存在 Chunk 中,它的组件定义了它的“能力和状态”。


三、Archetype:组件组合定义实体结构

当你给一个 Entity 添加了多个组件时,Unity 会自动根据这些组件的集合定义一个 Archetype。它可以理解为一个“结构签名”:

例如:

Archetype A = [Translation, Health, MonsterType]
Archetype B = [Translation, Velocity]

所有具有相同组件组合的 Entity 都属于同一个 Archetype。这样做的好处是:

  • 可以快速定位拥有某些组件的所有实体

  • 方便数据批处理

  • 支持结构化存储(方便内存布局)


四、Chunk:结构化内存块

每个 Archetype 拥有若干个 Chunk。Chunk 是 DOTS 中用于存储实体数据的最小单位。

Chunk 特点:

  • 大小固定为 16KB(Unity 内部固定)

  • 所有 Entity 的组件数据按列式存储

  • 每个 Chunk 只容纳一种 Archetype 的实体

  • 同一个 Chunk 中所有 Entity 的 SharedComponent 值必须一致

一个 Chunk 容纳多少个 Entity?

取决于每个 Entity 拥有组件数据的总大小。

例如:

  • Entity 每个数据 32B,则 Chunk 容纳 16KB / 32 ≈ 512 个

  • 若数据变大(如包含 float4x4),Entity 变少


五、SharedComponent:控制 Chunk 分类的关键

SharedComponent 是一种特殊的组件,实现了 ISharedComponentData 接口。它的值不能在 Entity 级别存储,而是存储在 Chunk 的 header 区域。

特性:

  • 所有 Chunk 内的 Entity 必须拥有相同的 SharedComponent 值

  • 值不同的 Entity 不能放在同一个 Chunk 中

  • 更改 SharedComponent 值会导致 Entity 搬家(Chunk 移动)

使用场景:

  • 怪物类型分类(如 MonsterType)

  • LOD 分组、区域分组、渲染材质分组(RenderMeshArray)

注意:频繁更改 SharedComponent 会引起性能抖动


六、为什么 Chunk 是 16KB?

这个数字是深思熟虑后的硬件适配值:

  • L1 Cache 一般为 32KB,每个 Chunk 16KB 可以保证高缓存命中率

  • L2 Cache 较大,也能容纳多个 Chunk

  • 16KB 是内存对齐、批处理、页管理的黄金折中值

太小:Entity 太少、效率低 太大:Cache 溢出、处理慢

因此 Unity 默认设定为 16KB,不可修改。


七、Archetype、Chunk、Entity 的组织结构图(文字版)

Archetype A: [Translation, Health, MonsterType]

├─ Chunk A1 (MonsterType = 1)
│ ├─ Entity 1
│ ├─ Entity 2
│ └─ ...

├─ Chunk A2 (MonsterType = 2)
│ ├─ Entity 1001
│ └─ ...
└─ ...

八、总结:设计背后的哲学

Unity DOTS 的 Archetype-Chuck-Entity 结构,融合了以下领域的精髓:

灵感来源 应用点
数据导向设计 DoD 构建 Archetype 以优化访问结构
列式数据库 Chunk 内组件按列排列
稀疏集合(Index+Version) 安全地管理 Entity 生命周期
GPU 渲染管线 SharedComponent 控制分组渲染

其核心目标是:利用现代硬件缓存特性,让大规模数据更新与处理高效而可控。


九、附:如何查看实际 Chunk/Archetype

  • 通过 Entities Hierarchy(Window → Entities)可视化工具查看 Chunk 分布

  • 通过代码:

EntityQuery query = GetEntityQuery(typeof(Health), typeof(MonsterType));
var chunks = query.ToArchetypeChunkArray(Allocator.Temp);
Debug.Log($"Archetype has {chunks.Length} chunks");

结语

你只是在 Mono 脚本里写了几行 AddComponent,Unity 在背后已经帮你构建好了复杂而高效的数据处理架构。这就是 DOTS 的魅力所在——开发者专注逻辑,系统保障性能。

理解 Archetype、Chunk、Entity 的内在原理,是走向 DOTS 高效架构设计的第一步。

从Mono脚本生成Entity:深入理解Unity DOTS中的Archetype、Chunk与Entity结构设计的更多相关文章

  1. QFramework 使用指南 2020(三):脚本生成(1)基本使用

    在上一篇,我们对 QFramework 的两个主要版本提供了介绍,并且写下了第一个 QFramework 脚本. 在这一篇,我们学习 QFramework 中几乎每个项目都要用到并且从中受益的功能:自 ...

  2. [转]全面理解Unity加载和内存管理

    [转]全面理解Unity加载和内存管理 最近一直在和这些内容纠缠,把心得和大家共享一下: Unity里有两种动态加载机制:一是Resources.Load,一是通过AssetBundle,其实两者本质 ...

  3. 理解Unity加载和内存管理

    转自:http://game.ceeger.com/forum/read.php?tid=4394#info Unity里有两种动态加载机制:一是Resources.Load,一是通过AssetBun ...

  4. C#生成DLL,在Unity中导入/调用DLL

    网上搜了一些DLL的创建.编写.使用的学习资料,感觉比较的凌乱.或是复杂抽象,或是关键地方一笔带过,不是很适合萌新.于是决定还是图文记录一下该过程,尽量精简而又明确. 学习资料: https://do ...

  5. [翻译]理解Unity的自动内存管理

    当创建对象.字符串或数组时,存储它所需的内存将从称为堆的中央池中分配.当项目不再使用时,它曾经占用的内存可以被回收并用于别的东西.在过去,通常由程序员通过适当的函数调用明确地分配和释放这些堆内存块.如 ...

  6. 【原创】使用批处理脚本生成包并自动上传到nuget

    Hello 大家好,我是TANZAME,我们又见面了. NuGet 是什么这里就不再重复啰嗦,园子里一搜一大把.今天要跟大家分享的是,在日常开发过程中如何统一管理我们的包,如何通过批处理脚本生成包并自 ...

  7. 全面理解Unity加载和内存管理

     全面理解Unity加载和内存管理http://game.ceeger.com/forum/read.php?tid=4394&fid=2&uid=6507 1.用简单的“for”循环 ...

  8. 关于 Unity 项目中的 Mono 堆内存泄露

    关于 Unity 项目中的 Mono 堆内存泄露 题记:这是补一篇应该在将近一年前就应该写的记录,今天终于补上. 内存泄露是一个老话题了,之前我专门写过一篇 排查 Lua 虚拟机内存泄露 的文章,并且 ...

  9. Unity脚本引用原理,修复Unity脚本引用丢失,源码脚本与dll中的脚本引用互换 .

    http://blog.csdn.net/gz_huangzl/article/details/52486509 前言 在我们开发游戏的过程中,经常会碰到脚本引用丢失的情况,但是怎么把它们修复到我们的 ...

  10. QFramework 使用指南 2020 (四):脚本生成(2)ViewController 与 ViewController 嵌套绑定

    在上一篇,我们学习了,脚本生成的基本使用. 在这一篇,我们试着深入,聊聊脚本生成给我们带来的便利. 脚本生成的便利 首先,我们要知道,在 Unity 的游戏世界中都是以 GameObject 为单位的 ...

随机推荐

  1. 【ROS】3.1 Turtlebot3汉堡Burger建SLAM地图并导航

    原视频 SLAM地图构建和导航 准备 本实验新用的功能包: 注意ros版本. sudo apt-get install ros-noetic-map-server # 用到map_server中的ma ...

  2. CatBoost算法原理及Python实现

    一.概述   CatBoost 是在传统GBDT基础上改进和优化的一种算法,由俄罗斯 Yandex 公司开发,于2017 年开源,在处理类别型特征和防止过拟合方面有独特优势.   在实际数据中,存在大 ...

  3. 部署Spring Boot项目详细教程

    首先Spring Boot项目能正常使用IP地址搭配接口在浏览器正常运行 第一步: 打开Maven里面Lifecycle下面的package或者是install双击运行(需要有网络) 第二步: 查看运 ...

  4. 100% 自主可控,Java Solon v3.3.1 发布(国产优秀应用开发基座)

    Solon 框架! Solon 是新一代,Java 企业级应用开发框架.从零开始构建(No Java-EE),有灵活的接口规范与开放生态.采用商用友好的 Apache 2.0 开源协议,是" ...

  5. React Native开发鸿蒙Next---图片浏览与保存的问题交流

    React Native开发鸿蒙Next---图片浏览与保存的问题交流 之前介绍过利用鸿蒙三方RN组件@react-native-camera-roll/camera-roll保存图片到相册. Rea ...

  6. Hyperledger Fabric出块配置详解

    Hyperledger Fabric的出块主要是Orderer节点负责,出块配置位于创世区块中,支持定时出块.达到一定交易数出块两种条件.出块配置位于configtx.yaml中,修改出块配置后需要重 ...

  7. anaconda基本操作及一些问题的解决记录

    anaconda虚拟环境 # anaconda 创建虚拟环境: conda create -n 虚拟环境名称 python=版本号 查看所有虚拟环境: conda env list 使用虚拟环境: c ...

  8. Coze工作流实战:一键生成像素风格视频

    前言 最近像素画风的视频非常火,一个视频浏览量超过10w+的也有很多. 那么这个是怎么实现的? 其实,通过AI工作流可以比较简单地实现这样的短视频. 今天给大家分享一下,我是如何搭建工作流实现的. 欢 ...

  9. 直播预约丨《袋鼠云大数据实操指南》No.3:数据资产管理实操,如何有效进行数据治理

    近年来,新质生产力.数据要素及数据资产入表等新兴概念犹如一股强劲的浪潮,持续冲击并革新着企业数字化转型的观念视野,昭示着一个以数据为核心驱动力的新时代正稳步启幕. 面对这些引领经济转型的新兴概念,为了 ...

  10. 谷歌浏览器 与 C# 4种嵌入浏览器 从 兼容性、性能、高级特性 方面的表现比对

    ​ CS架构 Web具有非常强大且友好的开发生态,在CS架构的窗口程序中嵌入浏览器,有哪些好处呢? 1,能够极大丰富程序的表现形式 2,能够充分地利用web的跨平台特性 3,能够使用web更现代更丰富 ...