所以我在我的人物收藏中收到了这些文件:
{
"_id" : ObjectId("595c0630939a8ae59053a9c3"),
"name" : "John Smith",
"age" : 37,
"location" : "San Francisco, CA",
"hobbies" : [
{
"name" : "Cooking",
"type" : "Indoor",
"regular" : true
},
{
"name" : "Baseball",
"type" : "Outdoor",
"regular" : false
}
]
}
{
"_id" : ObjectId("595c06b7939a8ae59053a9c4"),
"name" : "Miranda Thompson",
"age" : 26,
"location" : "Modesto, CA",
"hobbies" : [
{
"name" : "Lego building",
"type" : "Indoor",
"regular" : false
},
{
"name" : "Yoga",
"type" : "Indoor",
"regular" : false
}
]
}
{
"_id" : ObjectId("595c078e939a8ae59053a9c5"),
"name" : "Shelly Simon",
"age" : 26,
"location" : "Salt Lake City, UT",
"hobbies" : [
{
"name" : "Hunting",
"type" : "Outdoor",
"regular" : false
},
{
"name" : "Soccer",
"type" : "Outdoor",
"regular" : true
}
]
}
我正试图过滤我的爱好"数组仅限于常规爱好并投影字段_id,姓名,年龄和爱好的名称和类型。
我希望我的输出是这样的:
{
"_id" : ObjectId("595c0630939a8ae59053a9c3"),
"name" : "John Smith",
"age" : 37,
"hobbies" : [
{
"name" : "Cooking",
"type" : "Indoor"
}
]
}
{
"_id" : ObjectId("595c06b7939a8ae59053a9c4"),
"name" : "Miranda Thompson",
"age" : 26,
"hobbies" : []
}
{
"_id" : ObjectId("595c078e939a8ae59053a9c5"),
"name" : "Shelly Simon",
"age" : 26,
"hobbies" : [
{
"name" : "Soccer",
"type" : "Outdoor"
}
]
}
嗯......我可以在mongo shell中使用这个命令来实现这个输出:
db.people.aggregate([
{
$project: {
hobbies: {
$filter: {
input: "$hobbies",
as: "hobby",
cond: { $eq: ["$$hobby.regular", true] }
}
},
name: 1,
age: 1
}
},
{
$project: {
"hobbies.name": 1,
"hobbies.type": 1,
name: 1,
age: 1
}
}
])
正如你所看到的,我必须按顺序使用两个$ project操作符,我认为这闻起来很糟糕。
有没有办法用另一个查询来实现相同的结果,该查询没有按顺序使用同一个运算符两次?
答案 0 :(得分:7)
您可以将$filter
表达式包装在$map
中以映射输出值。
db.people.aggregate([
{
"$project": {
"name": 1,
"age": 1,
"hobbies": {
"$map": {
"input": {
"$filter": {
"input": "$hobbies",
"as": "hobbyf",
"cond": "$$hobbyf.regular"
}
},
"as": "hobbym",
"in": {
"name": "$$hobbym.name",
"type": "$$hobbym.type"
}
}
}
}
}
])