我使用以下查询来使用其位置获取下一个本地事件。我的数据库正在增长,我收到了来自欧洲各地的活动。所以基本上,查询计算距离两个不同国家(如西班牙和德国)的事件的距离,这是非常有用的,因为我正在寻找20公里内的下一个事件。
# latitude & longitude are the fields in DB
# 43.57 & 3.85 are given values representing the local test point
SELECT ( 6366 * ACOS( COS( RADIANS( 43.57 ) ) * COS( RADIANS( latitude ) ) * COS( RADIANS( longitude ) - RADIANS( 3.85 ) ) + SIN( RADIANS( 43.57 ) ) * SIN( RADIANS( latitude ) ) ) ) dist
FROM events
HAVING dist >0 AND dist <=20
ORDER BY event_time ASC
LIMIT 0 , 5
基本上,此查询将在能够使用HAVING
之前获取所有事件的所有距离。
有更好的方法吗?
答案 0 :(得分:2)
计算包围测试点周围半径的框的四个点的经度和纬度。在几公里的距离内,您可以忽略由于地球曲率引起的误差。
我们可以使用粗略近似来限制初始搜索,然后再改进。 在北纬50度(大致巴黎),纬度(北/南)约为111.229km。经度(东/西)约为71.695km(我从this page获得这些数字。从这20Km开始,纬度约为10.8秒,经度为16.74秒。通过加上和减去这些数字来计算边界框从测试点的纬度和经度开始。
使用经度和纬度查询该框中的位置。
如果你担心你的边界框可能太大,或者框中一个角落的事件在半径之外,那么为你已经识别的那些点计算一个准确的距离并滤除你的几个不想要。
注意强> 这些数字约为50度北。当你向北移动时,经度公里的价值将会变得太长,而南方的价值则会太短。您可以使用一个小的查找值表,或计算与纬度的实际距离,或者只是增加经度方向的初始边界框。这个盒子只是第一个近似值,所以只要它比目标区域大,它的确切大小就没那么重要了。