1.1 请解释 FVector 的 Normalize 和 GetSafeNormal 区别,以及 GetUnsafeNormal 的使用场景
★★ 中等考点: 向量归一化、零向量处理、UE API 设计
参考答案:
- 归一化将向量缩放为单位向量:
 = A / |A|,|A| = √(Ax² + Ay² + Az²); - 三种方式的区别:
Normalize():原地修改并返回旧长度,零向量会产生 NaN,最快;GetSafeNormal(Tolerance):返回新向量不修改原向量,零向量返回零向量(默认容差 KINDA_SMALL_NUMBER),稍慢;GetUnsafeNormal():返回新向量不修改原向量,零向量会产生 NaN,最快。
- 使用建议:
- 性能敏感的热循环(Tick)中,若能确保向量非零,用
GetUnsafeNormal()提性能; - 一般推荐
GetSafeNormal(),防止 NaN 传播污染后续计算; - 也可先算
Size()判断> KINDA_SMALL_NUMBER再除以长度,避免二次开方。
- 性能敏感的热循环(Tick)中,若能确保向量非零,用
- 代码示例:
FVector A(3.f, 4.f, 0.f);
float OldLen = A.Normalize(); // 原地修改,返回 5.0f,A=(0.6,0.8,0)
FVector C = A.GetSafeNormal(); // 返回新向量
FVector D = FVector::ZeroVector.GetSafeNormal(); // (0,0,0),安全
// FVector::ZeroVector.GetUnsafeNormal(); // (NaN,NaN,NaN),危险!
FVector Dir = Target - Source;
float Dist = Dir.Size();
if (Dist > KINDA_SMALL_NUMBER) Dir /= Dist; // 先判零再归一化,避免二次开方- 易错点:
GetUnsafeNormal产生的 NaN 会沿碰撞、动画等计算链传播导致异常;IsNormalized()可用于断言检查;比较距离时用SizeSquared()避免开方。