首页
学习
活动
专区
圈层
工具
发布
首页
学习
活动
专区
圈层
工具
MCP广场
社区首页 >问答首页 >在数组中选择和推送最后一个元素

在数组中选择和推送最后一个元素
EN

Stack Overflow用户
提问于 2014-06-17 14:18:21
回答 1查看 1.8K关注 0票数 1

我有以下结构的文件:

代码语言:javascript
运行
复制
{
...,
trials:[ {...,
          ref:[{a:1,b:2},{a:2,b:2},...]
         },
         {...,
          ref:[{a:1,b:2}]
         },
         ...,
       ]
}

其中ref是一个保证长度至少为1的数组。

如果我想计数每个ref数组中每个元素的个别出现情况,我将使用以下聚合。(这个很好)

代码语言:javascript
运行
复制
db.cl.aggregate([
   {$unwind:"$trials"},
   {$unwind:"$trials.ref"},
   {$group:{_id:"$trials.ref", count:{$sum:1}}}
])

现在,我想做同样的事情,但只对每个ref数组中的最后一个元素执行。我需要一种方法只选择聚合管道中每个数组的最后一个元素。

首先,我认为我可以添加一个中间步骤,通过这样的操作来获得我想要分组的所有元素:

代码语言:javascript
运行
复制
db.cl.aggregate([
   {$unwind:"$trials"},
   {$group:{_id:null,arr:{$push:"$trials.ref.-1"}}},...
])

我还尝试在$match中使用一个位置运算符。

代码语言:javascript
运行
复制
db.cl.aggregate([
    {$unwind:"$trials"},
    {$match:{"trials.ref.$":-1}},...
])

或者试图投射最后一个元素。

代码语言:javascript
运行
复制
db.cl.aggregate([
    {$unwind:"$trials"},
    {$project:{ref:"$trials.ref.1"}}
])

这两件都不让我有任何进展。$pop运算符在聚合管道中无效。$last运算符在这里并不是很有用。

对于如何只使用ref数组的最后一个元素有什么想法吗?我宁愿坚持使用聚合框架,而不使用Map。

EN

回答 1

Stack Overflow用户

发布于 2014-06-18 09:11:07

聚合框架实际上无法处理这个问题。除了缺少任何“片”类型操作符之外,这里真正的问题是缺乏任何标记来判断内部数组的结束位置,而且也没有任何其他形式的文档重新成形的方法。

至少就目前而言,mapReduce方法非常简单,甚至不需要还原剂:

代码语言:javascript
运行
复制
db.cl.mapReduce(
    function() {
        this.trials.forEach(function(trial) {
            trial.ref = trial.ref.slice(-1);
        });

        var id = this._id;
        delete this._id;

        emit( id, this );
    },
    function(){},
    { "out": { "inline": 1 } }
)

未来可能会有一些希望。某种形式的$slice已经被追捧了一段时间。但我确实注意到了$map 运算符码中的这个有趣的片段。我只想在这里列出:

代码语言:javascript
运行
复制
    output.reserve(input.size());
    for (size_t i=0; i < input.size(); i++) {
        vars->setValue(_varId, input[i]);

        Value toInsert = _each->evaluateInternal(vars);
        if (toInsert.missing())
            toInsert = Value(BSONNULL); // can't insert missing values into array

        output.push_back(toInsert);
    }

注意for循环和索引值。例如,我将投票将其公开为$map运算符中的变量,因为您知道数组的当前位置和长度,因此可以有效地进行“切片”。

但就目前而言,没有一种方法可以使用$map判断数组中的位置,而且如果您同时使用$unwind,则需要释放内部数组的端点。因此,目前缺乏聚合框架的解决方案。

票数 1
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/24266224

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档