为什么我们需要一个单位向量(换句话说,为什么我们需要对向量进行标准化)?

时间:2010-02-21 03:22:47

标签: c++ c math

我正在读一本关于游戏AI的书。

正在使用的术语之一是规范化矢量,该矢量将矢量转换为单位。为此,您必须将每个维度xyz除以其大小。

在我们做任何事情之前,我们必须把矢量变成一个单位。为什么?

并且有人可以给出一些我们必须使用单位向量的场景吗?

谢谢!

5 个答案:

答案 0 :(得分:32)

你不必对矢量进行标准化,但是当你这样做时,它会使很多方程变得更简单。它还可以使API更小:任何形式的标准化都有可能减少必要的功能。

这是一个简单的例子。假设您想要找到两个向量u和v之间的角度。如果它们是单位向量,则角度只是arccos(u v)。如果它们不是单位矢量,则角度为arccos(u v /(| u | | v |))。在这种情况下,你最终会计算出u和v的规范。

答案 1 :(得分:23)

正如John D. Cook所说 - 主要是你这样做是因为你关心方向,而不是矢量本身。根据具体情况,您很可能不希望/需要幅度信息 - 只需要方向本身。你规范化以消除幅度,这样它就不会扭曲其他计算,从而简化了许多其他事情。

就人工智能而言 - 想象你把P1(AI坏人)和P2(你的英雄)之间的向量V作为坏人移动的方向。你希望坏人以每节拍的速度N移动 - 你怎么计算这个?好吧,我们要么将每个节拍的矢量标准化,乘以N来计算它们移动了多远,或者我们首先将方向预先标准化,然后每次将单位矢量乘以N - 否则坏人会移动如果它离英雄更远!如果英雄没有改变位置,那么担心的计算就少了一个。

在这种情况下,这不是什么大问题 - 但如果你有一百个坏人呢?还是一千?如果你的AI需要处理坏人的组合怎么办?突然间,你每节拍节省了一百或几千个标准化。由于这是少数乘法和每个的平方根,最终你会达到不提前规范化数据的意义,这意味着你要杀死你的AI处理率。

更广泛地说 - 数学对此非常普遍 - 人们在这里做他们为3D渲染做的事情 - 如果你没有统一,例如,表面的法线,你可能有成千上万的规范化每次渲染都是完全没必要的。您有两个选择:一个 - 让每个函数执行计算,或者两个 - 预先标准化数据。

从框架设计者的角度来看:后者本来就更快 - 如果我们假设前者,即使你的用户想要规范化数据,他们也必须经历相同的规范化程序或者你要去每个功能都提供两个版本,这很令人头疼。但是,当你让人们考虑要调用哪个版本的函数时,你也可以让他们足够好地调用正确的函数,并且只在第一时间提供它,让它们为性能做正确的事情。 。

答案 2 :(得分:8)

您经常对矢量进行标准化,因为您只关心矢量指向的方向而不是幅度。

具体方案是Normal Mapping。通过组合照射表面的光线和垂直于表面的矢量,您可以给出一种深度的幻觉。来自曲面的矢量定义了平行方向,矢量的大小实际上会使计算错误。

答案 3 :(得分:6)

  

我们必须将矢量转换为单位   在我们做任何事情之前。

此声明不正确。所有向量都不是单位向量。

构成坐标空间基础的向量具有两个非常好的属性,使它们易于使用:

  1. 他们是正交的
  2. 他们是单位向量 - magnitude = 1
  3. 这使您可以将3D空间中的任何矢量写为单位矢量的线性组合:

    alt text http://www.equationsheet.com/latexrender/pictures/e691d8878d3d2cf83362af36faa16096.gif

    如果我需要将每个分量除以幅度

    ,我可以选择将此向量转换为单位向量

    alt text http://www.equationsheet.com/latexrender/pictures/78a0af48a0d02492fdd2b5377157c6a8.gif

    如果您不知道坐标空间或基础向量,我建议您在进一步学习之前先了解一下图形的数学知识。

答案 4 :(得分:0)

除了已经提供的答案之外,我还提到两个重要方面。

三角学在单位圆上定义

所有三角函数都是在单位圆上定义的。数字pi本身是在单位圆上定义的。

当您对矢量进行标准化时,您可以直接使用所有三角函数 ,而无需进行任何舍入。如前所述,两个单位向量之间的角度很简单:acos(dot(u, v)),没有进一步缩放。

Trigonometric Circle

单位矢量允许我们将大小与方向分开

矢量可以解释为携带两种信息的数量:幅度和方向。力,速度和加速度是重要的例子。

如果您希望单独处理 的大小和方向,请使用vector = magnitude * direction形式的表示形式,其中magnitude是标量,direction是一个单位矢量,通常非常方便:幅度的变化需要标量操作,方向的变化不会改变幅度。 direction必须是单位向量,以确保vector的幅度完全等于magnitude