用于碰撞检测的O(n ^ log n)算法

时间:2012-05-10 16:22:31

标签: c++ algorithm collision-detection time-complexity

我正在构建一个游戏引擎,我想知道:是否有任何算法用于碰撞检测,时间复杂度为O(N ^ log N)?

我还没有编写任何编码,但我只能想到一个O(N ^ 2)算法(即:2个循环遍历对象列表以查看是否存在冲突)。

任何建议和帮助将不胜感激。

由于

4 个答案:

答案 0 :(得分:3)

空间分区可以创建O(n log(n))解决方案。根据对象的确切结构和性质,您需要一个不同的空间分区算法,但最常见的是八叉树和BSP。

基本上,空间分区的想法是按对象占用的空间对对象进行分组。节点Y中的对象永远不会与节点X中的对象发生碰撞(除非X是Y的子节点,反之亦然)。然后,您可以对通过哪些节点的对象进行分区。我自己实现了一个八叉树。

答案 1 :(得分:2)

您可以通过将对象排序到空间区域来最小化检查次数。 (检查0,0附近的物体与1000,1000附近的物体之间的碰撞没有意义)

显而易见的解决方案是将您的空间成功地分成两半并使用树(BSP)结构。虽然这最适合稀疏的物体云,否则你会花费所有时间来检查边界附近的物体是否碰到了边界另一侧的物体

答案 2 :(得分:2)

我假设您有一个受限制的交互长度,即当两个对象是一定距离时,就没有更多的交互。 如果是这样,您通常会将空间划分为适当大小的域(例如,每个方向的交互长度)。现在,为了将交互应用于粒子,您需要做的就是通过自己的域和最近的相邻域,因为所有其他粒子都保证比交互长度更远。当然,您必须检查粒子更新是否跨越任何域边界,并相应地调整域成员身份。考虑到由于交互对数减少导致的巨大性能提升,这种额外的簿记是没有问题的。 对于更多技巧,我建议一本关于数值N-Body-Simulation的科学书籍。

当然,每个域都有自己的域中的粒子列表。在模拟中有一个中心粒子列表是没有用的,并且通过所有条目来检查每个粒子是在当前域还是相邻域中。

答案 3 :(得分:1)

我正在使用oct-tree作为3D中的位置,这可能是非常均匀分布的。树(重新)构建通常非常快,机器人O(N log(N))。然后找到给定粒子的所有碰撞可以在O(K)中完成,其中K是每个粒子的碰撞次数,特别是没有因子log(N)。因此,要在树构建之后找到所有碰撞,则需要O(K * N)。