我一直在寻找答案,但也许我只是没有使用正确的术语。我正在创建一个应用程序,它将访问数据库以返回在用户位置一定距离内的其他用户列表。我从来没有使用过这种类型的数据,我真的不知道这些值的含义。我想使用 MySQL 或 PHP 在后端进行所有计算。目前,我将纬度和经度作为双精度存储在数据库中。我可以访问它们并存储它们,但我不知道如何根据距离对它们进行排序。也许我应该使用该领域常见的不同类型或某种技术。TIA。
2 回答
听起来您需要使用haversine公式来获取两组长/纬度坐标之间的距离(调整地球曲率)。
如果您使用它作为输出运行查询,您可以轻松地根据与用户的最小距离对它们进行排序。
这是用 9 种常用语言实现hasrsine的链接,这是一个在 SQL 查询中实现它的 SO question 。
这是您可以适应的查询(从最近到最远的顺序获取 25 英里内的任何内容):
SELECT
id,
( 3959 * acos( cos( radians(37) ) * cos( radians( lat ) ) * cos( radians( lng ) - radians(-122) ) + sin( radians(37) ) * sin( radians( lat ) ) ) ) AS distance
FROM
markers
HAVING
distance < 25
ORDER BY
distance
LIMIT
0 , 20;
我建议使用 Vicenty 的逆公式(http://en.wikipedia.org/wiki/Vincenty 's_formulae)而不是 Haversine Great Circle 距离,因为 Vincenty 已被证明更准确(Vincenty 假设地球是一个扁球体一个完美的球体,这更准确)。
这是公式的原始文森蒂论文: http ://www.ngs.noaa.gov/PUBS_LIB/inverse.pdf - 第 4 节
这是来自 Android 平台的实际代码,用于计算 distanceTo(Location) 的距离,它使用 Vincenty 的反公式:https ://github.com/android/platform_frameworks_base/blob/master/location/java/android/location/位置.java#L272
至于基于数据库查询的排序距离,为了获得最佳性能,您需要使用允许空间查询的空间数据库。MySQL 有一个空间数据库插件: http ://dev.mysql.com/doc/refman/5.0/en/spatial-extensions.html
查看这篇文章,它应该为您提供从那里开始的详细信息,包括使用 Vicenty 的精度说明: PHP/MySQL 中的地理搜索(距离)(性能)