簡體   English   中英

改善空間MySQL查詢的性能

[英]Improving performance of spatial MySQL query

我有一個查詢,該查詢返回所有記錄,這些記錄按距固定點的距離進行排序,與MySQL 5.7數據庫中的POINT字段相比。

對於一個簡單的例子,可以說它看起來像這樣:

SELECT shops.*, st_distance(location, POINT(:lat, :lng)) as distanceRaw 
FROM shops 
ORDER BY distanceRaw
LIMIT 50

我的實際查詢還必須進行一些連接才能獲取結果的其他數據。

問題是,為了按距離對數據進行排序,它需要計算數據庫中每條記錄(當前大約100,000條記錄)的距離。

我無法緩存查詢,因為它僅特定於那些原始坐標。

無論如何,有沒有限制必須計算的數據? 例如,對附近商店進行可靠的粗略計算,例如lat + lng +/- 3度? 這樣它只需要處理一部分數據?

如果有人對這種優化有任何經驗,我很樂意提供一些建議,謝謝。

是的,您可以使用一些簡單的近似值,根據其中的條件來過濾掉半徑之外的那些位置。 這篇很棒的博客文章標題為“針對SQL(MySQL,PostgreSQL,SQL Server)的快速最近位置查找器”描述了這樣的優化:

請記住,根據本文前面的背景信息,緯度為111.045公里。 因此,如果我們在緯度列上有索引,則可以使用像這樣的SQL子句來消除太北或太南以至於50公里之內的點。

latitude BETWEEN latpoint - (50.0 / 111.045) AND latpoint + (50.0 / 111.045)

這個WHERE子句允許MySQL在計算hasrsine距離公式之前使用索引來省略很多緯度點。 它允許MySQL對緯度索引執行范圍掃描。

最后,我們可以使用類似但更復雜的SQL子句來消除太遠或太遠的點。 該子句更加復雜,因為經度越遠離我們移動的赤道,距離就越小。 這是公式。

longitude BETWEEN longpoint - (50.0 / (111.045 * COS(RADIANS(latpoint)))) AND longpoint + (50.0 / (111.045 * COS(RADIANS(latpoint))))

因此,將所有內容放在一起,此查詢將找到(緯度,經度)50公里邊界框內的近15個點。

上面描述了邊界矩形的理論背景。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM