mongodb - $lookup 后如何使用 $geoNear
问题描述
您好我有以下问题:我想使用 $geoNear (计算两点之间的距离)但在 $loopback 之后(以及我加入的集合)。这是 companyBases 集合的模型(我想加入它):
{
"_id" : ObjectId("5d7cfe13f42e7345d967b378"),
"location" : {
"type" : "Point",
"coordinates" : [
20.633856,
49.761268
]
},
"vehicles" : [
{
"_id" : ObjectId("5d7cfe13f42e7345d967b340"),
...other fields that doesn't matter
}
]
}
这是车辆集合:
{
"_id" : ObjectId("5d7cfe13f42e7345d967b340"),
...other fields that doesn't matter
}
我想加入 companyBase 集合以汇总车辆集合:
db.vehicles.aggregate([
{
$lookup: {
from: "companybases",
let: {
vehicleId: "$_id"
},
pipeline: [
{
$match: {
$expr: { $in: ["$$vehicleId", "$vehicles._id"] }
}
}
],
as: "companyBases"
}
},
{
$unwind: "$companyBases"
},
{
$geoNear: {
near: {
type: "Point",
coordinates: [50.02485, 20.0008]
},
distanceField: "distance",
spherical: true
}
}
]);
但它返回给我:
{
"message" : "$geoNear is only valid as the first stage in a pipeline.",
"operationTime" : "Timestamp(1568472833, 1)",
"ok" : 0,
"code" : 40602,
"codeName" : "Location40602",
"$clusterTime" : {
"clusterTime" : "Timestamp(1568472833, 1)",
"signature" : {
"hash" : "AAAAAAAAAAAAAAAAAAAAAAAAAAA=",
"keyId" : "0"
}
},
"name" : "MongoError"
}
当我在 companybases 集合上执行相同的管道时,它会返回具有计数距离的文档:
db.companybases.aggregate([
{
$geoNear: {
near: {
type: "Point",
coordinates: [50.02485, 20.0008]
},
distanceField: "distance",
spherical: true
}
}
]);
结果:
{
"_id" : ObjectId("5d7cfe13f42e7345d967b378"),
"location" : {
"type" : "Point",
"coordinates" : [
20.633856,
49.761268
]
},
"vehicles" : [
{
...some fields
},
],
...some fields
"distance" : 4209673.447019393
}
我意识到错误可能是由于车辆收集上缺少索引。那么有什么方法可以用 $geoNear 和 $lookup 计算距离吗?或者也许这是不可能的,我必须自己做?
解决方案
简单的解决方案(您可以将 $geoNear 放入 $lookup 管道中):
db.vehicles.aggregate([
{
$lookup: {
from: "companybases",
let: {
vehicleId: "$_id"
},
pipeline: [
{
$geoNear: {
near: {
type: "Point",
coordinates: [50.02485, 20.0008]
},
distanceField: "distance",
spherical: true
}
},
{
$match: {
$expr: { $in: ["$$vehicleId", "$vehicles._id"] }
}
}
],
as: "companyBases"
}
},
{
$unwind: "$companyBases"
}
]);
但这给性能留下了深刻的印象(至少需要 5 秒),因为在比赛前使用了 $geoNear。
推荐阅读
- spring-boot - 如何通过馈送客户端按原样交换已排序的数据
- python - 无法从模型的(数据库)中提取数据
- r - 为不同的列定义不同的时间序列
- php - 比较忽略空格、换行符、换行符的两个字符串
- c# - 异步等待某些任务完成 (Task.WhenSome)
- c# - 如何在 C# 中使用 MD5 哈希数据签署自己的 RSA 私钥
- spring-boot - 如何在 vue.js 中设置授权标头
- bash - 如何在 BASH 环境中将列中的数字列表替换为其他列中的随机数
- reactjs - Reactjs中的状态保存以前的状态值,如何用新编辑的表单值更新状态
- html - MVC 在视图中更改日期类型