o2o附近的商家功能常見的演算法:geohash和spatial4j調試實戰

2019年12月06日07:55:05 科技 1861

開篇

我調試了很多開源項目,包括開源商城、IM即時通訊等很多,感興趣的可以看看源碼點我頭像進去,覺得有用給個關注吧。

最近在看o2o相關的原理,網上說了很多geohash演算法的原理。但其實原理網上有很多,但真正的調試少之又少,今天就來寫代碼調試一下geo演算法和spatial4工具j。輕鬆實現,附近的商家功能。覺得有用,就點個贊轉個發吧。看文章的時候最好是跟著做,如果沒時間就收藏轉發吧。


o2o附近的商家功能常見的演算法:geohash和spatial4j調試實戰 - 天天要聞

geohash演算法原理簡單介紹

geo 是地理位置的geography 的縮寫,hash其實就是hash演算法。大家都知道,我們平常用的百度地圖,高德地圖其實每一個點都是有經緯度的。你可以理解為geohash,其實就是經緯度經過一些列運算出來的hash值,相似的經緯度得到的geohash值前綴幾乎一致,這樣就可以把一個區域內的點都可以直接在資料庫中查出來,當然具體原理自己可以去搜索。這裡就不介紹了,今天重點介紹,如何使用。

源碼可以到github上看:https://github.com/kungfoo/geohash-java


o2o附近的商家功能常見的演算法:geohash和spatial4j調試實戰 - 天天要聞

spatial4j工具

其實地球是球形的大家都知道,但基本上在地圖上你可以認為是平面。例如查詢附近1km的範圍你怎麼查呢?給定圓心坐標和半徑,求該圓外切正方形四個頂點的坐標。不是嗎?這個計算我們就用到spatial4j了。github上的地址是:https://github.com/locationtech/spatial4j


o2o附近的商家功能常見的演算法:geohash和spatial4j調試實戰 - 天天要聞

核心調試

1、建表,建工程

新建一個spring boot 工程,集成mybatis等,當然建個商戶表,有商戶名稱,經緯度,geohash等欄位。

CREATE TABLE `merchant` (
`id` INT(11) UNSIGNED NOT NULL AUTO_INCREMENT COMMENT '自增主鍵',
`merchant_name` VARCHAR(64) NOT NULL COMMENT '名稱',
`longitude` DOUBLE(9,6) NOT NULL COMMENT '經度',
`latitude` DOUBLE(8,6) NOT NULL COMMENT '緯度',
`geo_code` CHAR(12) NOT NULL COMMENT 'geohash編碼',
PRIMARY KEY (`id`),
KEY `idx_merchant_longitude_latitude` (`longitude`,`latitude`),
KEY `idx_merchant_geo_code` (`geo_code`)
)COMMENT='商戶表' CHARSET=utf8mb4 ENGINE=InnoDB;


o2o附近的商家功能常見的演算法:geohash和spatial4j調試實戰 - 天天要聞

2、方法一、查詢附近的1km的用spatial4j實現

A、首先引入jar包:

 <dependency>
<groupId>com.spatial4j</groupId>
<artifactId>spatial4j</artifactId>
<version>0.5</version>
</dependency>


o2o附近的商家功能常見的演算法:geohash和spatial4j調試實戰 - 天天要聞

B、計算四個點的的值

public static void main(String[] args) {
//起始點經緯度
double lon = 116.312528, lat = 39.983733;
// 千米
int radius = 1;
SpatialContext geo = SpatialContext.GEO;
Rectangle rectangle = geo.getDistCalc().calcBoxByDistFromPt(
geo.makePoint(lon, lat),
radius * DistanceUtils.KM_TO_DEG, geo, null);

System.out.println(rectangle.getMinX() +
"-" + rectangle.getMaxX());// 經度範圍
System.out.println(rectangle.getMinY() +
"-" + rectangle.getMaxY());// 緯度範圍
}


o2o附近的商家功能常見的演算法:geohash和spatial4j調試實戰 - 天天要聞

C、根據範圍,在資料庫中查找即可,查到附近1km的數據。當然,經緯度最好做聯合索引。這兩個數據是上面算出來的。

SELECT id, merchant_name
FROM merchant
WHERE (longitude BETWEEN ? AND ?) AND (latitude BETWEEN ? AND ?);

3、根據geohash查詢。此時會用到geo_code 欄位。

A、引入geohash的jar包

<!-- https://mvnrepository.com/artifact/ch.hsr/geohash -->
<dependency>
<groupId>ch.hsr</groupId>
<artifactId>geohash</artifactId>
<version>1.3.0</version>
</dependency>


o2o附近的商家功能常見的演算法:geohash和spatial4j調試實戰 - 天天要聞

B、對照geohash的長度對應範圍表,我們可以知道,查詢附近1km的數據,只要長度是5就可以了。具體計算,GeohashUtils.encodeLatLon(lat, lon, 5),代入底線sql即可。

SELECT id, merchant_name
FROM merchant
WHERE geo_code LIKE CONCAT(?, '%');

o2o附近的商家功能常見的演算法:geohash和spatial4j調試實戰 - 天天要聞

C、但geohash有邊界問題誤差。因為geohash是某個區域的共同的hash,索引邊界以外的距離很近的點可能造成geohash完全不同,那麼怎麼辦呢?其實也不難解決,你這個時候把周圍的八個區域的geohash都算出來即可。

public static void main(String[] args) {
// 移動設備經緯度
double lon = 116.312528, lat = 39.983733;
GeoHash geoHash = GeoHash.
withCharacterPrecision
(lat, lon, 6);
// 當前
System.out.println(geoHash.toBase32());
// N, NE, E, SE, S, SW, W, NW
System.out.println("---------------------------");
//東南西北,東北、西北、東南、西南等
GeoHash[] adjacent = geoHash.getAdjacent();
for (GeoHash hash : adjacent) {
System.out.println(hash.toBase32());
}
}

o2o附近的商家功能常見的演算法:geohash和spatial4j調試實戰 - 天天要聞


o2o附近的商家功能常見的演算法:geohash和spatial4j調試實戰 - 天天要聞

D、mysql查詢,查詢出這幾個區域的商家即可,geohash邊界問題就可以解決。

SELECT id, merchant_name
FROM merchant
WHERE geo_code IN (?, ?, ?, ?, ?, ?, ?, ?, ?);

結語

o2o中最常見的應用場景就是附近的商家,希望此篇文章對於o2o的同學有些幫助。覺得有用就點個贊轉發一下吧。

另外我還調試了其他很多開源項目

Java 開源的基於微服務 Spring cloud 快速開發腳手架調試實戰

超好用的 Java 開源 驗證碼 神器

Java 搭建的開源的spring boot商城系統實戰

前後端分離的開源在線考試系統調試實戰

調試個開源Java 輕量級高性能IM,單機支持幾十萬至百萬在線用戶

Java 百分之百開源 CMS 系統項目調試實戰

前端牛人寫的開源的CMS系統調試實戰,流體布局兼容手機端瀏覽器

覺得有用可以給個關注哦

科技分類資訊推薦

大疆OSMO 360 完整規格 7月29日發布 - 天天要聞

大疆OSMO 360 完整規格 7月29日發布

對於那些一直在等待大疆 Osmo 360 的人來說,聽到在本月底7月29日開售的消息,你們一定會很高興。今天我偶然發現了這兩款產品的完整網店描述和圖片已經上線。所以,我們先來深入了解一下那款「革命性 8K」 Osmo 360 的描述。
iPhone一鍵降溫?蘋果這隱藏模式有點過分啊 - 天天要聞

iPhone一鍵降溫?蘋果這隱藏模式有點過分啊

為了解決發熱這亘古難題,手機廠商絞盡腦汁,往手機里塞散熱膜、均熱板、填充硅脂,甚至還用上了主動風扇。 但到了夏天三四十度的室外,該發熱還是發熱,該燙手還是燙手。 國產安卓如此。 ....
三星Galaxy S26Ultra不裝了,性能太炸裂了! - 天天要聞

三星Galaxy S26Ultra不裝了,性能太炸裂了!

三星Galaxy S26 Ultra即將亮相,帶來多方面升級。·該機型將採用6.9英寸QHD+LTPO AMOLED顯示屏,支持120Hz自適應刷新率和3000尼特峰值亮度,確保在各種光照條件下都能提供清晰的視覺體驗。
中集洋山集裝箱第三季度訂單飽滿 開拓氫能集成裝備求新|公司調研 - 天天要聞

中集洋山集裝箱第三季度訂單飽滿 開拓氫能集成裝備求新|公司調研

財聯社7月5日訊(記者 胡皓瓊)中美關稅緩和之下,外貿企業對美出貨恢復,帶動中集洋山集裝箱製造訂單增長。集裝箱製造廠在提升自動化水平的同時,為提高自身抗風險能力,還正布局新賽道。財聯社記者近日走訪中集集團(000039.SZ)旗下中集洋山,眼見一片片鋼板,經歷衝壓、焊接組裝、打砂等一道道工序,逐漸成形。產線上布...
數據寶一體機實機首秀2025生態文明貴陽國際論壇 - 天天要聞

數據寶一體機實機首秀2025生態文明貴陽國際論壇

7月5日至6日,2025年生態文明貴陽國際論壇召開,數據寶攜其AI技術領先成果重磅亮相論壇人工智慧展區,並以「企業私域業務模型一體機」實機首秀,現場演繹數據資產與AI深度賦能綠色發展的創新融合實踐。數據寶「企業私域業務模型一體機」。
登上C909樣機,聽聽中國商飛工程總師怎麼說?《明青講習所》又上新了 - 天天要聞

登上C909樣機,聽聽中國商飛工程總師怎麼說?《明青講習所》又上新了

名師金課《明青講習所》今又上新,這期節目《「科學家精神」的迴響》聚焦於「科學家精神的時代傳承」,定於7月5日(周六)19:30 在上海教育電視台首播。陳明青老師帶領華東師範大學第一附屬中學、上海市魯迅中學、上海南湖職業技術學院的學生們,踏上沉浸式學習之旅,走進錢學森圖書館、中國商飛上海飛機設計研究院、上海科...