JavaScript 函数最近的地理邻居
Posted
技术标签:
【中文标题】JavaScript 函数最近的地理邻居【英文标题】:JavaScript function nearest geographical neighbor 【发布时间】:2013-05-27 14:04:24 【问题描述】:我正在寻找一个返回数字最近邻的 javascript 函数。例如:我有一个坐标 12,323432/12,234223,我想知道数据库中一组 20 个其他坐标的最近坐标。 如何处理?
【问题讨论】:
如果您没有具有适当功能的空间数据库,您可以“手动”计算所有坐标对之间的距离并取最小的一个。 为什么不在sql里做呢? 向我们展示您迄今为止为完成这项任务所做的工作。 到目前为止,我在代码中什么也没做。 Igor S 如何在 SQL 中做到这一点? 在你的数据库上安装postgis 【参考方案1】:以下 3 个函数使用 Haversine 公式从 javascript 数组中查找最近的坐标。
function toRad(Value)
/** Converts numeric degrees to radians */
return Value * Math.PI / 180;
function haversine(lat1,lat2,lng1,lng2)
rad = 6372.8; // for km Use 3961 for miles
deltaLat = toRad(lat2-lat1);
deltaLng = toRad(lng2-lng1);
lat1 = toRad(lat1);
lat2 = toRad(lat2);
a = Math.sin(deltaLat/2) * Math.sin(deltaLat/2) + Math.sin(deltaLng/2) * Math.sin(deltaLng/2) * Math.cos(lat1) * Math.cos(lat2);
c = 2 * Math.atan2(Math.sqrt(a), Math.sqrt(1-a));
return rad * c;
function calculate()
var result = haversine(lat1,coordArray [0][0],lng1,coordArray [0][1]);
for (var i=1;i<coordArray.length;i++)
var ans = haversine(lat1,coordArray [i][0],lng1,coordArray [i][1]);
if (ans < result)//nearest
result = ans;
document.write("Result " +result);
【讨论】:
【参考方案2】:使用文森蒂公式减少舍入误差
Haversine 公式 suffers from rounding errors 用于对映点的特殊(并且有些不寻常)情况(在球体的相对端)。
因此,更好的选择是the Vincenty formula for the special case of a sphere. 它在计算上的要求并不高,但受到机器舍入误差的影响较小。
这是我的 Python3 实现,它可以在任何使用 Brython 的浏览器中运行,或者可以轻松地手动转码为 JavaScript:
from math import radians, sin, cos, atan2, sqrt
def vincenty_sphere(lat1,lat2,lon1,lon2):
lat1 = radians(lat1)
lat2 = radians(lat2)
delta_lon = radians(lon2-lon1)
term1 = (cos(lat2) * sin(delta_lon))**2
term2 = (cos(lat1) * sin(lat2) - sin(lat1) * cos(lat2) * cos(delta_lon))**2
numerator = sqrt(term1 + term2)
denominator = sin(lat1) * sin(lat2) + cos(lat1) * cos(lat2) * cos(delta_lon)
central_angle = atan2(numerator, denominator)
radius = 6372.8 # km
return radius * central_angle
def station_near(geo):
lat = geo['latitude']
lon = geo['longitude']
nearest = 40042.0 # km
for s in range(len(STATIONS)):
distance = vincenty_sphere(lat, STATIONS[s].lat, lon, STATIONS[s].lon)
if(distance < nearest):
nearest = distance
station = s
return station
【讨论】:
以上是关于JavaScript 函数最近的地理邻居的主要内容,如果未能解决你的问题,请参考以下文章