Redis中地理位置GEO模塊,非常便捷的來查找附近的人或物

     從Redis3.2 版本以後,增加了地理位置 GEO 模塊,這個模塊提供了6個Geo指令,分別是geoadd、geodist、geopos、geohash、georadiusbymember及georadius,通過這個模塊的這些命令,可以用來實現平時開發需求當中的“附近的什麼什麼”,例如即時通訊中附近的人、外賣中附近的餐館、共享單車中附近的車等等。

地圖元素的位置數據使用經緯度表示,經緯度是經度與緯度的合稱組成一個座標系統,稱爲地理座標系統,它是一種利用三度空間的球面來定義地球上的空間的球面座標系統,能夠標示地球上的任何一個位置。經度範圍 (-180, 180],緯度範圍 (-90, 90],緯度正負以赤道爲界,北正南負,也是稱爲北緯和南緯,經度正負以本初子午線 (英國格林尼治天文臺) 爲界,東正西負,也是稱爲東經和西經。

無論人或者物,我們存儲這一個地理位置點的時候,會存儲元素 id,、經度 x,、緯度 y,當我們用關係型數據庫存儲時,計算兩點之間的距離時可以滿足需求的,如果要是給定一點,算出該點附近的點,那麼我們不可能通過遍歷來計算所有的元素和目標元素的距離然後再進行排序,這個計算量太大了,性能指標肯定無法滿足。臨時的解決方法就是通過矩形區域來限定元素的數量,然後對區域內的元素進行全量距離計算再排序,這樣可以明顯減少計算量。但是數據庫查詢性能畢竟有限,如果附近的功能查詢請求非常多,在高併發場合,這可能並不是一個很好的方案。

市場的需求,就是程序員努力提升自我能力的方向。IT界的解決方案,通常是層出不窮並且包羅萬象,對於地理位置距離排序,通常用的算法是 GeoHash 算法,Redis 也使用 GeoHash 算法。GeoHash 算法將二維的經緯度數據映射到一維的整數,這樣所有的元素都將在掛載到一條線上,距離靠近的二維座標映射到一維後的點之間距離也會很接近。當我們想要計算“附近的什麼”時,首先將目標位置映射到這條線上,然後在這個一維的線上獲取附近的點就行了。先來講一講Redis 的 Geo 指令基本使用:

1、geoadd:
語法:geoadd key longitude latitude member [longitude latitude member……]
功能:將給定的空間元素(維度、經度、名字)添加到指定的鍵裏面
2、geopos
語法:geopos key member [member……]
功能:從鍵裏面返回所有給定位置元素的位置(經度和維度)
3、geodist
語法:geodist key member1 member2 [unit]
功能:返回兩個給定位置之間的距離
4、georadius
語法:georadius key longitude latitude radius m|km|gt|mi [WITHCOORD] [WITHDIST] [WITHHASH] [ASC|DESC] [COUNT count]
功能:以給定的經緯度爲中心,返回鍵包含的位置元素當中,與中心的距離不超過給定最大距離的而所有位置元素。
選項:
WITHDIST:在返回位置元素的同時,將位置元素與中心之間的距離也一併返回。
WITHCOORD:將位置元素的經度和緯度也一併返回。
WITHHASH:以52位有符號整數的形式,返回位置元素經過原始geohash編碼的有序集合分值。這個選項主要用於底層應用或者調試,實際中的作用並不大。
ASC:根據中心的位置,按照從近到遠的方式返回位置元素
DESC:根據中心的位置,按照從遠到近的方式返回位置元素
5、georadiusbymember
語法:georadiusbymemeber key member radius m|km|ft|mi [WITHCOORD] [WITHDIST] [WITHHASH] [ASC|DESC] [COUNT count]
功能:這個命令和georadius命令一樣,不同的是中心點是由給定的位置元素決定的
6、geohash
語法:geohash key member [member……]
功能:返回一個或多個位置元素的geohash表示

下面我們來實際操作一下,比如查詢附近的公司,先來添加一些公司,可以使用百度的座標拾取器來獲取座標點:

geodist 指令可以用來計算兩個元素之間的距離,參數傳集合名稱、2 個名稱和距離單位。

geopos 指令可以獲取集合中任意元素的經緯度座標,可以一次獲取多個。

geohash 可以獲取元素的經緯度編碼字符串,上面已經提到,它是 base32 編碼。 你可以使用這個編碼值去 http://geohash.org/${hash} 中進行直接定位,它是 geohash 的標準編碼值。

georadiusbymember 指令是最爲關鍵的指令,它可以用來查詢指定元素附近的其它元素,按照我們上面說的語法可以來查詢附近的元素:

看來阿里離騰訊有些遠呀!

除了 georadiusbymember 指令根據元素查詢附近的元素,Redis 還提供了根據座標值來查詢附近的元素,這個指令更加有用,它可以根據用戶的定位來計算“附近的什麼”,這個指令就是georadius:

到此爲止,我們介紹了Redis的GEO地理模塊,也介紹了模塊中的指令及使用,是不是可以滿足需求中要開發“附近的什麼”的功能了?

 

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章