mongoDb地理空间索引和查询
一.MongoDb介紹(http://docs.mongoing.com/manual/applications/geospatial-indexes.html)
MongoDB提供了一系列的索引和查詢機制來處理地理空間信息。這一節會介紹MongoDB的地理索引特性。您可以閱讀地理索引教程來了解關于MongoDB中地理查詢的完整示例。
表面
在您存儲地理數據和編寫查詢條件前,首先,您必須選擇表面類型,這將被用在計算中。您所選擇的類型將會影響您的數據如何被存儲,建立的索引的類型,以及您的查詢的語法形式。
MongoDB提供了兩種表面類型:
球面
如果需要計算地理數據就像在一個類似于地球的球形表面上,您可以選擇球形表面來存儲數據,這樣就可以使用2dsphere索引。
您可以按照坐標軸:經度,緯度的方式把位置數據存儲為GeoJSON對象。GeoJSON的坐標參考系使用的是WGS84數據。
平面
如果需要計算距離,就像在一個歐幾里德平面上,您可以按照正常坐標對的形式存儲位置數據并使用2d索引。
位置數據
如果您選擇球形表面來計算,您可以選擇把位置數據存儲為如下兩種格式之一:
GeoJSON對象
對GeoJSON的查詢總是基于球形表面。GeoJSON的默認坐標參考系使用的是WGS84數據。
2.4 新版功能:在版本2.4新引入了對GeoJSON的存儲和查詢支持。在版本2.4以前,所有的地理數據使用坐標對的形式。
在 2.6 版更改:支持更多GeoJSON類型:多點, 多線段, MultiPolygon, 幾何體集合。
MongoDB支持如下GeoJSON對象:
單點
線段
多邊形
多點
多線段
MultiPolygon
幾何體集合
普通坐標對
MongoDB支持對使用2dsphere索引的legacy coordinate pairs(普通坐標對)數據進行球面計算,方式是把數據轉換成GeoJSON Point類型。
如果您選擇的是平面計算且使用2d索引,那么您可以把數據存儲為僅 :term:`legacy coordinate pairs`格式。
查詢操作
MongoDB地理空間查詢操作允許您查詢:
包含
MongoDB可以查詢被完全包含于一個指定多邊形區域中的位置。包含查詢使用的是$geoWithin操作符。
兩種索引2d和2dsphere索引都支持包含查詢。在版本2.2.3之后,對于包含查詢,MongoDB不再要求有索引。但是,這些索引可以提升查詢性能。
交叉
MongoDB可以查詢位置和一個指定幾何圖形的交叉。這些查詢僅可以被用于查詢存儲在球形平面上的數據。這些查詢使用$geoIntersects操作符。
只有2dsphere索引才支持交叉。
鄰近
MongoDB可以查詢和某個點最近的其他點。鄰近查詢使用$near操作符。$near操作符要求有2d或者2dsphere索引。
地理空間索引
MongoDB提供了如下的地理索引類型來支持地理查詢。
2dsphere
2dsphere索引可以支持如下特性:
在球形平面上的計算
GeoJSON對象和對普通坐標對的向后兼容。
復合索引。這個復合索引可以包含一個2dsphere索引字段以及一些按升序或降序建立的普通索引字段(作為2dsphere索引的前綴或者后綴)。
2.4 新版功能:在版本2.4之前``2dsphere`` 索引是不可用的。
參見
查詢 2dsphere 索引
2d
2d索引支持如下特性:
使用平面幾何的方式計算
普通坐標對(比如,在一個平面坐標系中的點)
作為復合索引,額外索引一個鍵。方法是,把額外的一個鍵作為2d索引鍵的后綴
參見
查詢 2d 索引
地理空間索引和分片
您不能使用地理索引來作為shard key索引。
您可以在一個被分片的集合上創建并維護一個一個地理空間索引,使用的不能是分片鍵。
對于被分片的幾何,使用了$near操作的查詢是不被支持的。作為替代,您可以使用geoNear命令或者$geoNear在聚合階段的時候。
您還可以使用$geoWithin來查詢地理空間數據。
其它資源
以下頁面提供了關于地理空間索引和查詢的完整文檔
2dsphere 索引
MongoDB的2dsphere索引支持查詢在一個類地球的球面上進行幾何計算。 索引支持以GeoJSON對象或者普通坐標對的方式存儲數據。
2d 索引
MongoDB的2d索引支持以普通坐標對的方式存儲數據,用于MongoDB2.2版及以前
geoHaystack 索引
haystack索引是一個被特殊優化過的索引,用于返回小區域結果。對于那些使用球面幾何的查詢而言,2dsphere會是一個更好的選擇。
2d 索引原理
提供了對地理索引更深層次本質的闡釋。這份材料對于普通操作者不是必須的,但是對于正在排除障礙或者想要更深入理解的用戶也許有點幫助。
參見
Geospatial Query Compatibility
二.示例
建立places集合,來存放地點, loc字段用來存放地區數據GeoJSON Point。
db.places.insert(
{
loc : { type: "Point", coordinates: [ -73.97, 40.77 ] },
name: "Central Park",
category : "Parks"
}
)
db.places.insert(
{
loc : { type: "Point", coordinates: [ -73.88, 40.78 ] },
name: "La Guardia Airport",
category : "Airport"
}
)
建立索引
db.places.ensureIndex( { loc : "2dsphere" } )
參數不是1或-1,為2dsphere。還可以建立組合索引。
db.places.ensureIndex( { loc : "2dsphere" , category : -1, name: 1 } )
3. 查詢
$geometry表示查詢的幾何圖片.
3.1 查詢多邊形范圍的值
type表示類型:polygon 多邊形
db.places.find( { loc :
{ $geoWithin :
{ $geometry :
{ type : "Polygon" ,
coordinates : [ [
[ 0 , 0 ] ,
[ 3 , 6 ] ,
[ 6 , 1 ] ,
[ 0 , 0 ]
] ]
} } } } )
3.2 查詢附近的值
使用$near來查詢附近的地點。
db.places.find( { loc :
{ $near :
{ $geometry :
{ type : "Point" ,
coordinates : [ <longitude> , <latitude> ] } ,
$maxDistance : <distance in meters>
} } } )
3.3 查詢圓形內的值
查詢圓時,需要指定圓心, 半徑。
db.places.find( { loc :
{ $geoWithin :
{ $centerSphere :
[ [ -88 , 30 ] , 10 ]
} } } )
[-88, 30] 為經緯度, 10為半徑。
地址:http://blog.csdn.net/yonggang7/article/details/28109463
二.項目中springMVC中是用mongoDb查詢范圍得點
2.1建立索引
//deliver數據
deliver:{
"deliverArea": [
{
"area": [
{
"district": "叢臺區",
"location": {
"lat": 36.613143702791,
"lng": 114.50521301419
},
"street": "朝陽路",
"street_number": "5號"
},
{
"district": "叢臺區",
"location": {
"lat": 36.612694686043,
"lng": 114.50516800908
},
"street": "朝陽路",
"street_number": "5號"
},
{
"district": "叢臺區",
"location": {
"lat": 36.612744657392,
"lng": 114.50573403138
},
"street": "朝陽路",
"street_number": "5號"
},
{
"district": "叢臺區",
"location": {
"lat": 36.61310669522,
"lng": 114.50577903649
},
"street": "朝陽路",
"street_number": "14號"
}
]
}
],
"deliverId": "D011122"
}
db.deliver.ensureIndex({"deliverArea.area.location":"2dsphere"})
2.2查詢命令
//mongoDB shell
db.deliver.aggregate([ { $geoNear: { near: { type: "Point", coordinates: [ 114.495539 , 36.597626 ] }, distanceField: "deliverArea.area.location", maxDistance: 10, num: 5, spherical: true } } ])
//spingMvc 使用Aggregation
Point location = new Point(114.495539 , 36.597626);
NearQuery query = NearQuery.near(location).maxDistance(new Distance(distance, Metrics.MILES)).num(5).spherical(true);
Aggregation aggregation = newAggregation( geoNear(query,"deliver") );
AggregationResults<Deliver> results = mongoTemplate.aggregate(aggregation,"deliver",Deliver.class);
//spring 使用MongoOperations Point location = new Point(-73.99171, 40.738868); NearQuery query = NearQuery.near(location).maxDistance(new Distance(10, Metrics.MILES)); GeoResults<Restaurant> = operations.geoNear(query, Restaurant.class);
使用MongoOperations GeoResults 返回的deliver list數據中,deliver會被content包裝,要取出deliver數據需content中取。
參考:http://docs.spring.io/spring-data/mongodb/docs/current/reference/html/
總結
以上是生活随笔為你收集整理的mongoDb地理空间索引和查询的全部內容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: 企业微信开发url回调成功后的对xml解
- 下一篇: 正益工场为京西创客工场输送双创“软”实力