我有以下文档结构:
{
"input": {
"fields": [
{
"name": "last_name_hebrew",
"text": "test1",
},
],
},
"output": {
"fields": [
{
"name": "last_name_hebrew",
"text": "test1"
},
],
},
},
我想获取所有文档,其中字段具有名称为 last_name_hebrew
的对象与 text
一样output.fields
的值(value).
例如在给定的结构中它会返回这个文件因为input.fields.name
是last_name_hebrew
和 text
等于 text
在 output
.
注意我不能保证 fields
input
中的数组或 output
会有name: last_name_hebrew
在数组中。
我该怎么做?
这是我尝试首先强制数组具有 name
的文档的 last_name_hebrew
:
db.collection.find({
"input.fields": {
$elemMatch: {
"name": "last_name_hebrew"
}
},
"output.fields": {
$elemMatch: {
"name": "last_name_hebrew"
}
},
})
但现在我需要比较 text
值(value)观。
最佳答案
$elemMatch
的前两个条件是正确的- 添加表达式匹配,首先使用
$filter
从input
中找到具有last_name_hebrew
名称的匹配元素,并从该过滤结果中获取第一个元素使用$arrayElemAt
,output
字段的过程相同,然后使用$eq
匹配两个对象
db.collection.find({
"input.fields": { $elemMatch: { "name": "last_name_hebrew" } },
"output.fields": { $elemMatch: { "name": "last_name_hebrew" } },
$expr: {
$eq: [
{
$arrayElemAt: [
{
$filter: {
input: "$input.fields",
cond: { $eq: ["$$this.name", "last_name_hebrew"] }
}
},
0
]
},
{
$arrayElemAt: [
{
$filter: {
input: "$output.fields",
cond: { $eq: ["$$this.name", "last_name_hebrew"] }
}
},
0
]
}
]
}
});
第二个选项:如果你想更具体地匹配精确的 2 个字段 name
和 text
都只需要添加 $let
运算符从过滤器返回字段,
db.collection.find({
"input.fields": { $elemMatch: { "name": "last_name_hebrew" } },
"output.fields": { $elemMatch: { "name": "last_name_hebrew" } },
$expr: {
$eq: [
{
$let: {
vars: {
input: {
$arrayElemAt: [
{
$filter: {
input: "$input.fields",
cond: { $eq: ["$$this.name", "last_name_hebrew"] }
}
},
0
]
}
},
in: { name: "$$input.name", text: "$$input.text" }
}
},
{
$let: {
vars: {
output: {
$arrayElemAt: [
{
$filter: {
input: "$output.fields",
cond: { $eq: ["$$this.name", "last_name_hebrew"] }
}
},
0
]
}
},
in: { name: "$$output.name", text: "$$output.text" }
}
}
]
}
})
第三个选项:为了更具体地检查循环中的两个字段,
- 首先使用 $filter 在输入字段中按名称过滤匹配的元素
- 将上述过滤器结果传递给另一个过滤器
- 过滤匹配输出字段中的名称和文本字段,如果不为[]空则返回过滤结果
$ne
检查返回结果是否为[]空
db.collection.find({
"input.fields": { $elemMatch: { "name": "last_name_hebrew" } },
"output.fields": { $elemMatch: { "name": "last_name_hebrew" } },
$expr: {
$ne: [
{
$filter: {
input: {
$filter: {
input: "$input.fields",
cond: { $eq: ["$$this.name", "last_name_hebrew"] }
}
},
as: "i",
cond: {
$ne: [
{
$filter: {
input: "$output.fields",
cond: {
$and: [
{ $eq: ["$$this.name", "$$i.name"] },
{ $eq: ["$$this.text", "$$i.text"] }
]
}
}
},
[]
]
}
}
},
[]
]
}
})
关于MongoDB 获取数组值匹配的所有文档,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/66801727/