找到两个移动物体的更好交点

时间:2012-04-27 21:20:03

标签: javascript algorithm math optimization geometry

我想优化其中一个算法,我会尝试以最好的方式解释它。

主题

我们在 t = 0 时处于2D欧几里德系统中。 在这个系统中有两个对象: O1 O2

O1 O2 分别位于 PA PC 点。

O1 PB 点的方向上以恒定且已知的速度移动。当物体到达PB时,物体将停止。

O2 可以在任何方向上以恒定且已知速度不同或不的O1移动。在0时,O2有没有方向,我们需要为它找到一个。

知识参数:

  • O1:位置,方向,速度
  • O2:位置,速度

这是系统的一个小图。

Diagram of the system

我们希望找到 PI 点和时间 ti Position of O1 at the time ti = Position of O2 at the time ti = PI。然后我们将对象O2移动到PI点以获得 O2方向

当选择O2的方向(点PI)且移动的物体O1和O2时,对象将永远不会停止或等待

在这种情况下,结果将是这样的(PI在此图片上标注为D)。 Best intersection

算法

你可以在jsfiddle找到用JS编写的工作算法,这也是理解这个问题的好方法。

此时我使用一个简单的算法,但是可以进行大量的操作,我会获得最佳的交叉时间,然后获得交叉位置。

为了得到这个时间,我会立刻检查O1的位置,并检查此时O2是否可能到达此位置。如果O2无法及时到达目标,我们会将时间增加150%,但如果O2当时可以越过O1-B线,我们将把时间缩短50%。

最终,经过多次近似,我们将找到两个物体相遇的最佳时间。

伪代码

function getOptimalIntersectionTime time
   if distance between O1 and O2 at the time `time` < 1
       return time
   else if O2 could not reach the object O1 at the time `time`
       return getOptimalIntersectionTime time * 1.5
   else
       return getOptimalIntersectionTime time * 0.5

为什么我要关注?

我的算法有效,但在某些情况下(例如jsFiddle中的“反向案例”),需要大量的微积分才能找到最佳点。

在这个jsFiddle中,我们使用的是位置(-1000到1000)和速度(1-200)的小值,但是这个算法在数字越大时就越慢。

我知道过早优化是一个坏主意,但我在项目的最后(包括数据库插入/选择和数据分析,包括这个算法多次调用),这个算法最多需要80在某些情况下,项目系统的百分比会重新获得资源,因此改进可以真正提高系统的稳定性和响应能力。

4 个答案:

答案 0 :(得分:9)

不失一般性,让O2位于(0,0)。

sv为O1的位置和速度向量,v2为O2的速度,t为拦截时间。然后我们有:

|s + v * t| = t * v2

根据距离的定义:

(sx + vx * t) ^ 2 + (sy + vy * t) ^ 2 = (t * v2) ^ 2

将此乘以及重新排序的术语给出:

  sx^ 2 + 2 * sx * vx * t + vx^2 * t^2
+ sy^ 2 + 2 * sy * vy * t + vy^2 * t^2
-                           v2^2 * t^2
= 0

  sx^2 + sy^2 + (2 * sx * vx + 2 * sy * vy) * t + (vx^2 + vy^2 - v2^2) * t^2 = 0
  \---   ---/   \------------   ----------/       \--------   ------/
      \ /                    \ /                           \ /
       c                      b                             a

如您所见,这是t中的二次方程。我们可以简单地应用quadratic formula来找到t的两个可能值(如果等式没有解,那是因为没有拦截是可能的)。您可能希望使用最早的未来拦截,即较小的t>&gt; 0.

一旦你计算了t,就找到拦截点,并且截取方向应该很容易。

总而言之,这个问题可以在恒定时间内解决,不需要迭代。

答案 1 :(得分:1)

你似乎过分思考问题,它应该只是简单的几何。

不考虑如何定义最近点的问题,让我们解决所需点位于PAPB之间的情况。

我们必须假设整个周期的时间段,我们称之为T

PI = (PB - PA) / 2;  // simplified
TI = T / 2;          // simplified

[分别分解x和y坐标的所有公式]。

确定点(PC)与线(PA - > PB)的最近交点有相对简单的公式,但是当该线不是无限长时,它的定义是如何复杂的。

然后你需要:

V1 = (PB - PA) / T;  // O1's velocity
V2 = (PI - PC) / T;  // O2's velocity

最后两行不依赖于先前的假设 - 如果你知道截取点,那么速度就是行进的距离除以所花费的时间。

因此,除非你对V2施加一些额外的约束,否则总是一个解决方案,并且它是在几个简单的数学运算中计算的。

答案 2 :(得分:1)

更新:@Meriton后来的回答比我好。我建议尝试他的第一个。

如你所知,我们在三个未知数vx2,vy2和t中分别有三个联立方程 - 分别是02和x的y和y速度。遗憾的是,这些方程式并非都是线性的:

x1o + vx1*t == x2o + vx2*t
y1o + vy1*t == y2o + vy2*t
vx2*vx2 + vy2*vy2 == vy*vy

(这里,x1o,y1o,x2o和y2o是初始位置的坐标。)

如果有办法线性化问题,我看不到它。然而,您可以通过相同的Newton-Raphson technique GPS使用来迭代地快速解决,从而根据卫星信号计算您的位置。当然,要填写细节并实施这将需要一些工作!

更新:认为 @Alnitak可能已经相当整齐地线性化了您的问题。也许他的方法和我的方法的组合因此会繁荣。 (我仍然认为你会想要使用Newton-Raphson迭代来收敛@ Altinak的T。)

答案 3 :(得分:0)

由于速度是固定的,这应该可以使用并行导航的思想来解决。这样想吧。在时间0,在O1和O2之间存在一条线(LOS或视线)。如果O2遵循最佳交叉路径,则在时间1,O1和O2之间的线将与时间0 LOS平行。由于您具有O2的速度,您可以计算它在时间0和时间1之间行进的距离,并且可以计算它与时间1 LOS相交的位置。想想在O2的原始位置周围划一圈,其半径等于它在该时间间隔内行进的距离。该圆与第二个LOS的交叉点将包含解决方案。如果没有相交,则没有解决方案。这本在线书的开头有一个图表和公式,显示了这个概念:

http://www.crcnetbase.com/doi/abs/10.1201/9781420062281.ch2

此问题具有真实世界的应用程序,您可能也会发现此解决方案。例如,潜艇可以使用它来绘制并保持与目标的拦截航线,方法是在目标靠近目标时保持目标的LOS方向不变。

编辑:

enter image description here

此图显示了我在说什么。这可以使用三角函数来解决,除了目标O1直接朝向或远离导弹O2移动的特殊情况(可以通过简单的方法解决)。

在上图中,我们可以花费一些任意的时间。在那个时间t1期间,O1将具有行进距离b,并且O2将具有行进距离f。在时间t0,O1和O2之间的线与在时间t1的O1和O2之间的线平行。由于我们给出了O1和O2的初始位置,我们知道距离d,因为我们得到了O1的方向,我们可以简单地计算角度A.

So given A, b, f, and d, using the law of Cosines,
a = sqrroot(c^2 + b^2 - (2cb * cos(A)))
and
B = arccos((a^2 + c^2 - b^2)/2ac)
Using the law of Sines
E = arcsin((a * sin(B))/f)  or the ambiguous value of 180 - that value
and with that
BC = 180 - E   (because C = 180 - B - E so C+B = 180 - E
对于BC,我们有解,并且可以类似地计算O1和O2的初始位置的三角形的任何其他方面和交点。 自从我使用高中三年以来已经很多年了,所以我可能会错过这个简化,但这有希望解释我最初描述的解决方法。