Unreal Engine 4 —— UE4的内存模型杂七杂八
2017-08-03 17:31
1476 查看
这篇博客介绍了UE4的内存模型相关的东西与我在运用UE4时相关的一些心得。
由于整个内存模型比较复杂,因此这篇博客的点可能会比较散乱……可能日后会进行整理(也可能不会)
UE4运行的基本单位是
可以通过如下代码来获得一个
Cluster指得是一组
每一个
引擎中有一个全局变量
但很奇怪的,在我新建的若干个测试关卡/项目中,这个值一直为0……
一个关卡
虽然
一度看了看Reference是怎么跑起来的,后来发现大部分的从UClass派生出来的类会制定对应的
<未完待续>
由于整个内存模型比较复杂,因此这篇博客的点可能会比较散乱……可能日后会进行整理(也可能不会)
UObject
和FUObjectItem
UE4运行的基本单位是UObjet,然而
UObject针对于内存相关的东西都储存在结构体
FUObjectItem中。有个全局变量
GUObjectArray,可以通过以下代码来遍历所有的Objects:
for (FRawObjectIterator It(false); It; ++It) { FUObjectItem* ObjectItem = *It; UObject* obj = ObjectItem->Object; }
可以通过如下代码来获得一个
UObject对应的
ObjectItem
FUObjectItem* ObjectItem = GUObjectArray.ObjectToObjectItem(Object);
GUObjectArray中有几个函数可以通过索引和ObjectItem、Object的相互获取,对应的函数为
IndexToObject、
ObjectToIndex、
IndexToObjectUnsafeForGC等。
GUObjectArray中所有的
UObjectArray的分布是有顺序的——那些不会被GC的
UObject,例如各StaticClass、核心Object,GamePlayInstance等会放在前面;而那些有可能被GC的
UObject,则放在后面。此外,
GUObjectArray中有个变量
ObjLastNonGCIndex,用于分隔这两类
UObject。
/** * Returns true if this object is "disregard for GC"...same results as the legacy RF_DisregardForGC flag * * @param Object object to get for disregard for GC * @return true if this object si disregard for GC */ FORCEINLINE bool IsDisregardForGC(const class UObjectBase* Object) { return Object->InternalIndex <= ObjLastNonGCIndex; }
FUObjectCluster
相关
Cluster指得是一组UObject为一簇,这群
UObject同生共死,每个Cluster有一个根
root的
UObject。
每一个
FUObjectItem里面有一个变量
ClusterRootIndex,这个储存的是当前Object所在的Cluster的root object所在
GUObjectArray的索引。
// UObjectArray.h // UObject Owner Cluster Index int32 ClusterRootIndex;
引擎中有一个全局变量
FUObjectClusterContainer GUObjectClusters,用于管理内存中所有的Clusters。
// Get the number of all clusters that have been allocated. GUObjectClusters.GetNumAllocatedClusters()
但很奇怪的,在我新建的若干个测试关卡/项目中,这个值一直为0……
一个关卡
ULevel不可以成为一个Cluster的root,原因是在这个时候(postload之后)仍然有很多被Level引用的assets并未构建它们自己的Cluster。
bool ULevel::CanBeClusterRoot() const { // We don't want to create the cluster for levels in the same place as other clusters (after PostLoad) // because at this point some of the assets referenced by levels may still haven't created clusters themselves. return false; }
虽然
ULevel本身不可以作为Cluster Root,而相反的是它会创建一个特殊的actor container,用来储存原本应该位于Cluster的actors。这是由于只有某些特殊的actor种类才能用于Cluster,所以剩下的那些不能被cluster的actors需要通过actor container来进行引用。
ULevel中使用ClusterActors数组用于储存那些用于Cluster的Actors;用ActorsForGC储存那些剩下的Actors。主食中提到不希望Level直接去引用那些本就是Cluster的Actors,注释中提到这会导致变慢(针对于cluster的Reference很慢,可能是如果引用了cluster里面的actor,那么会导致整个cluster也会添加对应的引用关系,从而导致引用的层级变多吧……)
TArray<AActor*> ClusterActors; for (int32 ActorIndex = Actors.Num() - 1; ActorIndex >= 0; --ActorIndex) { AActor* Actor = Actors[ActorIndex]; if (Actor && Actor->CanBeInCluster()) { ClusterActors.Add(Actor); } else { ActorsForGC.Add(Actor); } }
引用相关
如何获得一个UObject所引用的其他
UObject?
TArray<UObject*> CollectedReferences; FReferenceFinder ObjectReferenceCollector(CollectedReferences); ObjectReferenceCollector.FindReferences(Object);
一度看了看Reference是怎么跑起来的,后来发现大部分的从UClass派生出来的类会制定对应的
ClassAddReferenceObjects方法,这个方法用于制定该类会和哪些东西产生对应的引用……
<未完待续>
相关文章推荐
- UE4房产应用虚拟样板间功能演示 | 3D箭头移动 | 材质替换 | 模型拖拽移动 - Unreal Engine 4
- 【UNREAL ENGINE 游戏开发】开篇之UE4的BLUEPRINT(蓝图)与C++(新童鞋必看)
- UE4 UnrealEngine中多台电脑 拼接 随机物体的 同步 输出 高清 立体 视频
- Unreal Engine 4 动态切割模型实现
- Ubuntu 14.04 编译 Unreal Engine 4 (UE4)
- 【UE4官方文档翻译】Unreal Engine 4 For Unity Developers (针对Unity开发者的UE4)
- 虚幻引擎4(Unreal Engine 4/UE4)正式发布!每月19美元
- Unreal Engine 4(UE4)下载教程
- Unreal Engine 4 —— Kajiya-Kay Shading在UE4中的实现
- Unreal Engine 4 —— Kajiya-Kay Shading在UE4中的实现
- “Unreal Engine 4 - 使用ProceduralMeshComponent实现模型实时切割”无效的问题解决
- Unreal Engine 4 UE4 CAVE 立体 Stereo cluster 多通道立体渲染 沉浸式环境 displaywall powerwall
- Java虚拟机 - 体系结构 内存模型
- C++ Q&A(三) C++的内存模型
- 详细介绍c++中的类对象内存模型
- JVM内存模型以及堆分配参数
- java 内存模型的基础
- Redis 哈希结构内存模型剖析
- Unreal Engine 4 —— Physically Based Materials
- JVM内存模型和垃圾收集