2d 索引原理¶
On this page
这篇文档对MongoDB的 2d 地理索引提供了更深层次的内在机制解释。这份材料对于普通操作或者应用开发并不是必要的,但是对于故障排除或者想要更多了解的用户也许有用。
为 2d 索引计算Geohash值¶
当您基于 普通坐标 创建索引,MongoDB会在给定 位置范围 内的为坐标计算 geohash 并索引该geohash值。
为了计算geohash, 需要迭代地把一个二维区域划分为四个象限。然后,给每个象限赋予一个2-bit值。例如,四个象限的2-bit值如下:
01 11
00 10
这些2-bit值 (00, 01, 10, 11) 分别代表了一个象限和在这个象限内的所有点。求解时,所有在左下角象限的点将会拥有geohash 00. 左上角象限的点的geohash会是 01 .依此类推,右下角和右上角的geohash分别是 10 和 11 。
为了能更精确的索引,继续把每个象限划分为子象限。 每个子象限也一样会有geohash, 由父象限的geohash和子象限的geohash拼接在一起。右上角象限的geohash是 11 ,所以它的子象限的geohash将是(从左上开始,顺时针方向) 1101 , 1111 , 1110 , 和 1100 。
多个位置数据的文档的 2d 索引¶
注解
2dsphere indexes can cover multiple geospatial fields in a document, and can express lists of points using MultiPoint embedded documents.
While 2d geospatial indexes do not support more than one geospatial field in a document, you can use a multi-key index to index multiple coordinate pairs in a single document. In the simplest example you may have a field (e.g. locs) that holds an array of coordinates, as in the following example:
db.places.save( {
locs : [ [ 55.5 , 42.3 ] ,
[ -74 , 44.74 ] ,
{ lng : 55.5 , lat : 42.3 } ]
} )
数组中的元素坐标, 可以是数组形式, 如
您可以在 locs 键上创建一个地理索引如下:
db.places.createIndex( { "locs": "2d" } )
也许,您把位置数据建模为子文档中的一个键。在这种情况下,文档中应该有一个键(例如 addresses ) 存储了子文档数组, 其中每篇子文档都有一个键(例如 loc: )存储着位置坐标。如下:
db.records.save( {
name : "John Smith",
addresses : [ {
context : "home" ,
loc : [ 55.5, 42.3 ]
} ,
{
context : "work",
loc : [ -74 , 44.74 ]
}
]
} )
那么, 您可以在 addresses.loc 键上创建地理索引,如下:
db.records.createIndex( { "addresses.loc": "2d" } )
To include the location field with the distance field in multi-location document queries, specify includeLocs: true in the geoNear command.