[英]Finding documents in mongodb collection by order of elements index of array field
Array field in collection:集合中的数组字段:
"fruits": [ "fruits": [ "fruits": [
{"fruit1": "banana"}, {"fruit2": "apple"}, {"fruit3": "pear"},
{"fruit2": "apple"}, {"fruit4": "orange"}, {"fruit2": "apple"},
{"fruit3": "pear"}, {"fruit1": "banana"}, {"fruit4": "orange"},
{"fruit4": "orange"} {"fruit3": "pear"} {"fruit1": "banana"}
]
I need to find those documents in collections, where "banana" signed before "apple".我需要在 collections 中找到那些文件,其中“banana”在“apple”之前签名。 Does mongodb allows to compare elements in array just like:
mongodb 是否允许像这样比较数组中的元素:
if (fruits.indexOf('banana') < fruits.indexOf('apple')) return true;
Or maybe there is any other method to get result i need?或者也许还有其他方法可以获得我需要的结果?
MongoDB's array query operations do not support any positional search as you want. MongoDB 的数组查询操作不支持您想要的任何位置搜索。
You can, however, write a $where
query to do what you want:但是,您可以编写一个
$where
查询来执行您想要的操作:
db.yourCollection.find({
$where: function() {
return (this.fruits.indexOf('banana') < this.fruits.indexOf('apple'))
}
})
Be advised though, you won't be able to use indexes here and the performance will be a problem.不过请注意,您将无法在此处使用索引,并且性能会成为问题。
Another approach you can take is to rethink the database design, if you can specify what it is you're trying to build, someone can give you specific advise.您可以采取的另一种方法是重新考虑数据库设计,如果您可以指定要构建的内容,有人可以给您具体的建议。
One more approach: pre-calculate the boolean value before persisting to DB as a field and query on true / false.另一种方法:在将 boolean 值作为字段持久化到 DB 并查询 true / false 之前预先计算。
Consider refactoring your schema if possible.如果可能,请考虑重构您的模式。 The dynamic field names(ie fruit1, fruit2...) make it unnecessarily complicated to construct a query.
动态字段名称(即 fruit1、fruit2...)使构造查询变得不必要地复杂。 Also, if you require frequent queries by array index, you should probably store your array entries in individual documents with some sort keys to facilitate sorting with index.
此外,如果您需要通过数组索引进行频繁查询,您可能应该将数组条目存储在带有一些排序键的单个文档中,以便于使用索引进行排序。
Nevertheless, it is achievable through $unwind
and $group
the documents again.然而,它可以通过
$unwind
和$group
文件再次实现。 With includeArrayIndex
clause, you can get the index inside array.使用
includeArrayIndex
子句,您可以获得数组内的索引。
db.collection.aggregate([
{
"$unwind": {
path: "$fruits",
includeArrayIndex: "idx"
}
},
{
"$addFields": {
fruits: {
"$objectToArray": "$fruits"
}
}
},
{
"$addFields": {
"bananaIdx": {
"$cond": {
"if": {
$eq: [
"banana",
{
$first: "$fruits.v"
}
]
},
"then": "$idx",
"else": "$$REMOVE"
}
},
"appleIdx": {
"$cond": {
"if": {
$eq: [
"apple",
{
$first: "$fruits.v"
}
]
},
"then": "$idx",
"else": "$$REMOVE"
}
}
}
},
{
$group: {
_id: "$_id",
fruits: {
$push: {
"$arrayToObject": "$fruits"
}
},
bananaIdx: {
$max: "$bananaIdx"
},
appleIdx: {
$max: "$appleIdx"
}
}
},
{
$match: {
$expr: {
$lt: [
"$bananaIdx",
"$appleIdx"
]
}
}
},
{
$unset: [
"bananaIdx",
"appleIdx"
]
}
])
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.