假设数据库包含数以万计的具有以下结构的文档
{
_id: ObjectId("5ef053e819aaa00013a2bd69"),
approvers: [
{
type: "ONE",
details: {
name: "NameOne",
surname: "SurnameOne"
}
},
{
type: "TWO",
details: {
name: "NameTwo",
surname: "SurnameTwo"
}
},
{
type: "THREE",
// details field is missing
}
]
}
我只需要选择没有“TWO”或“ONE”类型的批准人或批准人缺少详细信息的此类文档
我有一个想法$not
结合使用$elemMatch
:
{
$or: [
{
"approvers.type": {
$not: {
$in: ["ONE", "TWO"]
}
}
},
{
approvers: {
$not: {
$elemMatch: {
type: { $in: ["ONE", "TWO"]},
details: {$exists: true}
}
}
}
}
]
}
该查询有效,但由于未使用索引,因此非常无效。根据我的理解,数据库引擎必须进行完整的集合扫描,并在每个文档中检查所有数组元素。
实际上该集合有 75k 条记录,每个approvers
数组最多可以容纳 3 个元素。
是否有任何“技巧”可以使其更有效,或者唯一的选择是更改数据结构?
这是分离收集有益的地方
假设以上是项目,可以采用不同的结构
//approvals
[{
_id: ObjectId
projectId: ObjectId // etc the _id in your code
type: "one",
details: "some stuff"
},
{
_id: ObjectId
projectId: ObjectId // etc the _id in your code
type: "two",
details: "some stuff"
},
{
_id: ObjectId
projectId: ObjectId // etc the _id in your code
type: "three",
details: "some stuff"
}]
然后,您可以在使用 $in 检索相关项目之前获取键入 $ne ["one", "two"] 的所有 projectId。尽管我从未尝试过,但这也应该可以通过聚合来实现。
本文收集自互联网,转载请注明来源。
如有侵权,请联系 [email protected] 删除。
我来说两句