选择子文档中数组的最后一个值 [英] Select last value of array in sub document
问题描述
我具有以下文档结构
{
"_id" : 1,
"prices" : {
"100" : [
5.67,
.
.
1.7,
],
"101" : [
4.67,
.
.
1.4,
},
"v" : 2
}
我们需要从字段"100"和"101"中获取最后一个值,例如1.7& 1.4,使用mongodb v3.0.2.当前,我们正在加载整个文档,然后在应用程序中获取所需的值.由于每个文档可能约为1MB,这已经成为一个瓶颈,对于100多个文档而言,这总共是一个瓶颈.
We need to get the last value from each of the fields "100" and "101", e.g 1.7 & 1.4, using mongodb v3.0.2. Currently we are loading the whole document and then getting the required values in the application. It has become quite a bottleneck as each document may be ~1MB, which for 100s of documents is adding up.
我们希望mongodb有一个合适的功能,它将使我们能够从文档中检索我们需要的数据,可能作为对每个价格字段的单独调用,即,一个对价格"100"键的调用,然后对第二个价格字段的调用要求输入价格"101"键.
We are hoping there is a suitable feature of mongodb that will allow us to just retrieve the data we need from the document, possibly as a separate call for each price field, i.e one call for the price "100" key and second call for the price "101" key.
我们已经尝试过使用$ slice运算符,但是很遗憾,它不能与排除字段一起使用, https ://jira.mongodb.org/browse/SERVER-3378 .
We have experimented using the $slice operator but this unfortunately cannot be used with exclusion fields, https://jira.mongodb.org/browse/SERVER-3378.
我们还看到了以下帖子: 如何结合使用这两个$ slice并在功能更新中选择返回的键操作?
We have also seen the following post: How to combine both $slice and select returned keys operation in function update?
几乎可以使用,但是查询的返回值:
Which almost works, but the return value from the query:
db.account_articles.find({"_id" : ObjectId("1")}, { "prices.100" : { $slice: -1 }, "_id" : 1 })
是:
{
"_id" : 1,
"prices" : {
"100" : [
1.7
],
"101" : [
4.67,
.
.
1.4,
}
}
即这是90%的方式,我们只需要能够排除"101"字段即可.
i.e. it's 90% of the way there, we just need to be able to exclude the "101" field.
我们遗漏了一些东西吗,或者在monogodb中是不可能的吗?
Are we missing something or is this not possible in monogodb?
推荐答案
您需要聚合框架来执行此操作,我认为您确实应该更改结构,但要使用已有的东西:
You need the aggregation framework to do this, I think you really should change the stucture, but working with what you have:
Model.aggregate(
[
{ "$match": { "prices.100": { "$exists": true } }},
{ "$unwind": "$prices.100" },
{ "$group": {
"_id": "$_id",
"price": { "$last": "$prices.100" }
}},
{ "$project": { "_id": 0, "prices.100": "$price" } }
]
)
在将来的版本中,您将只能使用新的$slice
运算符:
In future releases you will be able to just use the new $slice
operator:
Model.aggregate(
[
{ "$match": { "prices.100": { "$exists": true } } },
{ "$project": {
"_id": 0,
"prices.100": { "$slice": ["$prices.100",-1] }
}}
]
)
实际上,您可以同时执行两个"字段:
In fact you can do "both" fields at the same time:
Model.aggregate(
[
{ "$match": { "prices.100": { "$exists": true } } },
{ "$project": {
"_id": 0,
"prices.100": { "$slice": ["$prices.100",-1] },
"prices.101": { "$slice": ["$prices.100",-1] }
}}
]
)
这比使用 $unwind
和 $last
> 在 $group
用于获取数据.
And that is a lot better than processing with $unwind
and $last
to get the last element of the array when $group
is applied to get the data back.
它基本上具有与较新形式的常规查询相同的性能.在当前形式下,它会变慢.
It basically has the same performance as a regular query in the newer form. In the present form, it's going to be slower.
这篇关于选择子文档中数组的最后一个值的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!