使用st_distance在mysql中按距离对用户进行排序

时间:2015-03-04 11:52:54

标签: php mysql geolocation geospatial

我已经对此进行了一些阅读,但几乎没有关于使用mysql中的点和st_distance函数进行此操作的信息。我认为这是有道理的,因为根据http://bugs.mysql.com/bug.php?id=70494,它直到去年中期才被记录下来。我所看到的几乎所有解决方案都使用单独的长列和纬度列,然后将它们放入这样的半正式公式中:sorting distance in MySQL PHP这似乎是一种非常混乱的方式,尽管由于存在几何数据类型和空间函数。

到目前为止我的表是:

用户名 - varchar

位置 - 点(1 1)或类似的东西

我想选择一个用户,然后向他们显示最近的10个左右的用户。是否可以通过SQL使用points和st_distance函数完全执行此操作,或者我是否必须进行一些更改并使用hasrsine公式?

2 个答案:

答案 0 :(得分:1)

  

是否可以通过SQL使用points和st_distance函数完全执行此操作,或者我是否必须进行一些更改并使用hasrsine公式?

正如Geometry Class所述:

  

Geometry是层次结构的根类。它是一个不可实例化的类,但具有许多属性,如以下列表所述,这些属性对于从任何Geometry子类创建的所有几何值都是通用的。

[ deletia ]
     

所有计算都是在假设欧几里得(平面)几何的情况下完成的。

[ deletia ]
     

例如,在不同的坐标系中,即使对象具有相同的坐标,两个对象之间的距离也可能不同,因为 平面 坐标系上的距离和 地心 系统上的距离(地球表面上的坐标)是不同的东西。

因此,MySQL的空间扩展(包括其ST_Distance()函数)无法用于计算geodesics,例如great-circle distance,这就是您所追求的。正如您所推断的那样,您将不得不使用Haversine之类的公式。

Google Developers网站上有一个很好的教程:Creating a Store Locator with PHP, MySQL & Google Maps

答案 1 :(得分:0)

CREATE FUNCTION fnDistanceMiles(lat1 DECIMAL(12, 7),
                                lon1 DECIMAL(12, 7),
                                lat2 DECIMAL(12, 7),
                                lon2 DECIMAL(12, 7))
RETURNS DECIMAL(16, 8)
BEGIN

DECLARE DISTANCE DECIMAL(11, 4) DEFAULT 0;

SELECT 69.04117454 *
       DEGREES(ACOS(LEAST(COS(RADIANS(lat1))
                          * COS(RADIANS(lat2))
                          * COS(RADIANS(lon1 - lon2))
                          + SIN(RADIANS(lat1))
                          * SIN(RADIANS(lat2)), 1.0)))
INTO DISTANCE;

RETURN DISTANCE;

END;

DELIMITER ;