我有一个奇怪的mongodb文档,但仍然需要查询它。有可能吗?
例如:我需要一定范围内的每个玩家。
{
"_id" : ObjectId("55d89c63c746230c200c528e"),
"speler_id" : 12,
"naam" : "Arjen Robben",
"seconds" : [
[
{
"locatie" : [
8.7173307286181370,
33.2784843816214250
],
"timestamp" : ISODate("1970-01-01T19:00:01.000Z")
},
{
"locatie" : [
-45.8853075448968970,
138.1526615469845800
],
"timestamp" : ISODate("1970-01-01T19:00:02.000Z")
},
{
"locatie" : [
80.5503710377444690,
10.0500048843973580
],
"timestamp" : ISODate("1970-01-01T19:00:03.000Z")
}
]
]
}
答案 0 :(得分:0)
您可以随$geoWithin
或$center
使用$centerSphere
(取决于这些是全局几何坐标还是仅用于平面,以便进行距离校准),然后使用{{进行处理3}}在聚合框架中:
db.collection.aggregate([
{ "$unwind": "$seconds" },
{ "$unwind": "$seconds" },
{ "$match": {
"seconds.locatie": {
"$geoWithin": {
"$centerSphere": [
[
8.7173307286181370,
33.2784843816214250
],
100
]
}
}
}}
])
所呈现的数据将返回:
{
"_id" : ObjectId("55d89c63c746230c200c528e"),
"speler_id" : 12,
"naam" : "Arjen Robben",
"seconds" : {
"locatie" : [
8.717330728618137,
33.278484381621425
],
"timestamp" : ISODate("1970-01-01T19:00:01Z")
}
}
{
"_id" : ObjectId("55d89c63c746230c200c528e"),
"speler_id" : 12,
"naam" : "Arjen Robben",
"seconds" : {
"locatie" : [
80.55037103774447,
10.050004884397358
],
"timestamp" : ISODate("1970-01-01T19:00:03Z")
}
}
由于$geoWithin
不“需要”地理空间索引,因此可以在以后的聚合阶段使用,而不是初始匹配。在这种情况下,$centerSphere
定义了一个要查询的点和从该点延伸的“半径”。这只是一个几何“快捷方式”,因为您可以交替提供您自己定义的GeoJSON多边形。
但它并不是很棒。而且主要是因为它无法使用索引,因此对整个集合来说几乎是一种蛮力,并且你不能做很好的事情,例如返回查询点的距离,就像你可以用{{3}做的那样}。
因此,虽然您可以执行此类操作,但使用MongoDB的大多数地理空间查询最好留下将位置数据保留在文档的顶层,而不是嵌入到数组中。因此,这种建模通常意味着拥有单独的集合对象而不是嵌入集合对象,以获得最佳结果。
如果您希望在响应中使用聚合数组,那么在进行初始地理空间查询后,最好在聚合中执行此操作。