我在MongoDB中有表示圆的数据,如下所示:

{
    "_id" : ObjectId("54c1dc6506a4344d697f7675"),
    "location" : [
        23.027573,
        72.50675800000001
    ],
    "radius" : 500
}

我想用lat&long查询,以确定位置是否使用存储的lat&long和radius。
我尝试了以下查询,但无法执行:
db.test.find({location:{ $geoWithin: { $center: [ [ -74, 40.74 ] ,
                                                         "$radius"] } }})

如何在geoinquery中使用存储半径?

最佳答案

甚至比原来的更为理想,您现在可以在初始$expr之后的$match阶段中使用$geoNear

db.collection.aggregate([
    { "$geoNear": {
        "near": {
            "type": "Point",
            "coordinates": [ 23.027573, 72.50675800000001 ],
        },
        "distanceField": "distance"
    }},
    { "$match": { "$expr": { "$lte": [ "$distance", "$radius" ] } }}
])

实际上比第一次写的时候要好一点。现在我们可以$redact而不是$project布尔值和$match以后:
db.collection.aggregate([
    // Match documents "near" the queried point
    { "$geoNear": {
        "near": {
            "type": "Point",
            "coordinates": [ 23.027573, 72.50675800000001 ],
        },
        "distanceField": "distance"
    }},

    // Calculate if distance is within radius and remove if not
    { "$redact": {
        "$cond": {
            "if": { "$lte": [ "$distance", "$radius" ] },
            "then": "$$KEEP",
            "else": "$$PRUNE"
        }
    }}
])

您已经准确地存储了应该如何存储的信息,但是有一种不同的方法可以获得比您想象的结果。
你想要使用的是一个$geoNear并且特别是那个操作符的aggregation framework形式。你要做的是:
db.collection.aggregate([
    // Match documents "near" the queried point
    { "$geoNear": {
        "near": {
            "type": "Point",
            "coordinates": [ 23.027573, 72.50675800000001 ],
        },
        "distanceField": "distance"
    }},

    // Calculate if distance is within radius
    { "$project": {
        "location": 1,
        "radius": 1,
        "distance": 1,
        "within": { "$lte": [ "$distance", "$radius" ] }
    }},

    // Match only documents within the radius
    { "$match": { "within": true } }
])

因此,表单允许在结果中“投影”到查询点的距离,同时查询也只返回最近的文档。
然后使用逻辑比较查看“距离”值是否小于“半径”,因此在圆内。
最后,匹配以筛选出“within”断言为真的结果。
您可以向$geoNear添加其他选项,如文档中所示。我还强烈建议您的存储也应该使用geojson格式,因为它可能更兼容用于处理所获得结果的任何其他库。

10-04 21:30
查看更多