计算许多地理点之间距离的算法

时间:2012-01-19 06:46:17

标签: algorithm google-maps google-maps-api-3 geometry geospatial

我有一个矩阵,大约有1000个地理空间点(经度,纬度),我试图找到1KM范围内的点。

注意:“这些点是动态的,想象1000辆车正在移动,所以我必须每隔几秒重新计算所有距离”

我做了一些搜索并阅读了像(Floyd-Warshall)这样的Graph算法来解决这个问题,最后我找到了很多关键词,现在我有点迷失了。我正在考虑性能,因为搜索半径很短,我不会考虑地球的曲率。

基本上,似乎我必须计算每个点到每个其他点之间的距离,然后从矩阵中的每个点开始对距离进行排序,并获得其范围内的点。因此,如果我有1000个坐标,我必须执行此过程(1000 ^ 2-1000)次,我不相信这是最佳解决方案。谢谢。

7 个答案:

答案 0 :(得分:6)

如果你制作一个间距为1km的网格的模型:

  0   1    2    3
 ___|____|____|____
0   |    |    |
   c|   b|a   |   d
 ___|____|____|____
1   |    |    |
    |    |f   |
 ___|e___|____|____
2   |    |g   | 

让我们假设你的出发点是。 如果您的网格大小为1千米,则1公里范围内的点必须位于同一个小区或8个邻居之一(点b,d,e,f)。

可以忽略每个其他单元格(c,g)。

虽然d与c的距离几乎相同,但是c可以提前下降,因为有两个障碍可以穿越,而a和d位于其边界的相对区域,因此离距离近2 km彼此。

对于元素的早期删除,可以排除,只需检查坐标的x或y部分即可。由于a属于(0,2),如果x为0或更小,或者> 3,该点已经超出范围。

仅过滤少数候选人后,您可以使用详尽的搜索。

答案 1 :(得分:2)

在您的情况下,您应该查看GeoHash,它允许您快速查询给定距离内的坐标。

仅供参考,MongoDB在内部使用geohash并且表现非常出色。

答案 2 :(得分:1)

尝试使用R-Tree。 R-Tree支持操作以找到最接近给定点的所有不远离给定半径的点。执行时间是最佳的,我认为它是O(number_of_points_in_the_result)。

答案 3 :(得分:0)

您可以在这1000个坐标的每个坐标周围计算1km范围的地理编码,并检查某些点是否在该范围内。可能它不是最佳的,但你会省去一些分类。

答案 4 :(得分:0)

如果你想查找每个点与每个点的矩阵,那么你已经得到了正确的公式(1000 ^ 2-1000)。此计算没有任何快捷方式。但是,当您知道从何处开始搜索并希望查找1KM半径内的点时,可以使用网格或空间算法来加速查找。最有可能的是它使用分而治之的算法,其中最便宜的是geohash或z曲线。您也可以尝试kd树。也许这更简单。但是如果你的点位于euklidian空间,那么这里描述的是平面方法:http://en.wikipedia.org/wiki/Closest_pair_of_points_problem

编辑:当我说1000 ^ 2-1000时,我的意思是网格的大小,但它实际上是1000 ^(1000 - 1)/ 2对点,所以数学要少得多。

答案 5 :(得分:0)

我认为,在我工作的网页上,我有类似的东西。用户单击地图上的位置并输入半径,函数返回给定半径内数据库中的所有位置。你是说你想找到距离半径中一个点1公里范围内的点?或者您是否想要找到彼此相距1公里的点?我认为你应该这样做。

radius = given radius
x1 = latitude of given point;
y1 = longitude of given point;
x2 = null;
y2 = null;
x = null;
y = null;
dist = null;

for ( i=0; i<locationArray.length; i++ ) {
    x2 = locationArray[i].latitude;
    y2 = locationArray[i].longitude;
    x = x1 - x2;
    y = y1 - y2;
    dist = sqrt(x^2 + y^2);
    if (dist <= radius)
        these are your points
}

如果你试图计算距离另一个点1km范围内的所有点,你可以添加一个外部循环,给出x1和y1的信息,然后使内部循环测试给定点和每个其他点给出矩阵中的每个点作为输入。计算不应该花太长时间,因为它是如此基础。

答案 6 :(得分:0)

我遇到了同样的问题但是在Web服务开发中 在我的情况下,为了避免计算时间问题,我使用了一个简单的划分&amp;征服解决方案:这个想法是开始计算每个新数据插入中新点和其他点之间的距离,以便我的应用程序直接访问已经计算并放入我的数据库的那些拖点之间的距离