六一的部落格


关关难过关关过,前路漫漫亦灿灿。



创建两个Actor对象,并用两个指针指向

一个指针只在C++中使用; 另一个使用UPROPERTY宏标记, 受辖于垃圾内存回收机制


C++中创建对象


添加数据成员: Actor类型

protected

1UPROPERTY(EditAnywhere)
2TSubclassOf<AGeometryObject> GeometryClassForGarbageCollector;

添加数据成员: 指针

private

使用UPROPERTY宏标记的, 归垃圾回收机制管理

1AGeometryObject *NonePropertyGeometry;
2
3UPROPERTY()
4AGeometryObject *PropertyGeometry;

添加函数成员: 创建Actor对象

private

 1void AGeometryHub::SpawnGeometryForGarbageCollector()
 2{
 3    UWorld *World = GetWorld();
 4    if (World)
 5    {
 6        FTransform Transform = FTransform(FRotator::ZeroRotator, FVector(600.0f, 400.0f, 800.0f));
 7        NonePropertyGeometry = World->SpawnActor<AGeometryObject>(GeometryClassForGarbageCollector, Transform);
 8        Transform = FTransform(FRotator::ZeroRotator, FVector(600.0f, 800.0f, 800.0f));
 9        PropertyGeometry = World->SpawnActor<AGeometryObject>(GeometryClassForGarbageCollector, Transform);
10    }
11}

添加函数成员: 输出指针情况

private

在Tick中调用

输出指针情况

1void AGeometryHub::PrintPointerStatus()
2{
3    UE_LOG(LogGeometryHub, Log, TEXT("property pointer %i, is valid %i"), PropertyGeometry != nullptr, IsValid(PropertyGeometry));
4    UE_LOG(LogGeometryHub, Log, TEXT("nonproperty pointer %i, is valid %i"), NonePropertyGeometry != nullptr, IsValid(NonePropertyGeometry));    
5}

垃圾内存回收

Garbage Collector

负责定期清理内存

当Actor对象或组件被销毁时,使用UPROPERTY宏标记的指针会被置空, 无论指针指向对象或组件

TheBasics项目的最后一个内容点


设置Garbage Collector间隔

Project Settings > Engine > Garbage Collection > Time Between Purging Pending Kill Objects

当前61.1s

开销不小,不建议频繁触发


关卡的蓝图编辑器

Level Blueprint

不建议在关卡的蓝图编辑器添加实现 :

  1. 对关卡蓝图的了解不够
  2. 难以追踪逻辑的执行

打开关卡的蓝图编辑器



按下Enter时从场景中删除所有指定类型的Actor对象

  1. 添加事件: 按下键盘 Enter



  2. Pressed 出发: 获取场景中指定类型的所有Actor对象

    设置ActorClass为GeometryObject


  3. 从OutActors出发: 遍历数组


    接下来执行ForEachLoop


  4. 从ArrayElement出发: 对每个元素调用DestroyActor


    接下来执行DestroyActor



按下Tab时立即回收内存

  1. 添加事件: 按下键盘 Tab



  2. 从Pressed出发: 立即回收内存

    调用CollectGarbage




效果图


保存并编译


查看日志

  1. 运行程序



  2. 按下Enter Actor从场景中消失

    Actor对象的PendingToKill被置1,等待垃圾回收器回收内存



  3. 按下Tab 立即回收内存

    使用UPROPERTY宏标记的指针被置空

    仅在C++中使用的指针变做空悬指针,指向无效内存


垃圾内存回收机制


创建两个Actor对象,并用两个指针指向

一个指针只在C++中使用; 另一个使用UPROPERTY宏标记, 受辖于垃圾内存回收机制


C++中创建对象


添加数据成员: Actor类型

protected

1UPROPERTY(EditAnywhere)
2TSubclassOf<AGeometryObject> GeometryClassForGarbageCollector;

添加数据成员: 指针

private

使用UPROPERTY宏标记的, 归垃圾回收机制管理

1AGeometryObject *NonePropertyGeometry;
2
3UPROPERTY()
4AGeometryObject *PropertyGeometry;

添加函数成员: 创建Actor对象

private

 1void AGeometryHub::SpawnGeometryForGarbageCollector()
 2{
 3    UWorld *World = GetWorld();
 4    if (World)
 5    {
 6        FTransform Transform = FTransform(FRotator::ZeroRotator, FVector(600.0f, 400.0f, 800.0f));
 7        NonePropertyGeometry = World->SpawnActor<AGeometryObject>(GeometryClassForGarbageCollector, Transform);
 8        Transform = FTransform(FRotator::ZeroRotator, FVector(600.0f, 800.0f, 800.0f));
 9        PropertyGeometry = World->SpawnActor<AGeometryObject>(GeometryClassForGarbageCollector, Transform);
10    }
11}

添加函数成员: 输出指针情况

private

在Tick中调用

输出指针情况

1void AGeometryHub::PrintPointerStatus()
2{
3    UE_LOG(LogGeometryHub, Log, TEXT("property pointer %i, is valid %i"), PropertyGeometry != nullptr, IsValid(PropertyGeometry));
4    UE_LOG(LogGeometryHub, Log, TEXT("nonproperty pointer %i, is valid %i"), NonePropertyGeometry != nullptr, IsValid(NonePropertyGeometry));    
5}

垃圾内存回收

Garbage Collector

负责定期清理内存

当Actor对象或组件被销毁时,使用UPROPERTY宏标记的指针会被置空, 无论指针指向对象或组件

TheBasics项目的最后一个内容点


设置Garbage Collector间隔

Project Settings > Engine > Garbage Collection > Time Between Purging Pending Kill Objects

当前61.1s

开销不小,不建议频繁触发


关卡的蓝图编辑器

Level Blueprint

不建议在关卡的蓝图编辑器添加实现 :

  1. 对关卡蓝图的了解不够
  2. 难以追踪逻辑的执行

打开关卡的蓝图编辑器



按下Enter时从场景中删除所有指定类型的Actor对象

  1. 添加事件: 按下键盘 Enter



  2. Pressed 出发: 获取场景中指定类型的所有Actor对象

    设置ActorClass为GeometryObject


  3. 从OutActors出发: 遍历数组


    接下来执行ForEachLoop


  4. 从ArrayElement出发: 对每个元素调用DestroyActor


    接下来执行DestroyActor



按下Tab时立即回收内存

  1. 添加事件: 按下键盘 Tab



  2. 从Pressed出发: 立即回收内存

    调用CollectGarbage




效果图


保存并编译


查看日志

  1. 运行程序



  2. 按下Enter Actor从场景中消失

    Actor对象的PendingToKill被置1,等待垃圾回收器回收内存



  3. 按下Tab 立即回收内存

    使用UPROPERTY宏标记的指针被置空

    仅在C++中使用的指针变做空悬指针,指向无效内存