【问题标题】:Need to aggregate by hour and $avg not recognized需要按小时汇总,$avg 无法识别
【发布时间】:2015-11-14 10:06:28
【问题描述】:

从存储带有时间戳的数据的 MongoDB 集合中,我需要每小时返回一条记录。

到目前为止,我已经成功地选择了两个日期之间的记录集,但是我不知道如何在$group 子句中构建我需要的每小时记录。

var myName = "CollectionName"
//schema for mongoose
var mySchema = new Schema({
    dt: Date,
    value: Number
});

var myDB = mongoose.createConnection('mongodb://localhost:27017/MYDB');

myDBObj = myDB.model(myName, evalSchema, myName);

此聚合调用中的匹配工作正常,$hour 为一天中的每个小时创建一条记录.. 但我不知道如何重新创建完整日期并收到错误 "unknown group operator $avg" .. .

myDBObj.aggregate([
        {
            $match: { "dt": { $gt: new Date("October 13, 2010 12:00:00"), $lt: new Date("November 13, 2010 12:00:00") } }
        },{
            $group: {
            "_id": { "dt": { "$hour": "$dt" } , "price": { "$avg": "$price" }}

        }], function (err, data) { if (err) { return next(err); } res.json(data); });

我想我需要使用$dayOfYear,因此每天每个小时都有不同的记录,并在某处包含new Date() ...

有人可以帮我正确地做到这一点吗?任何帮助表示赞赏。

【问题讨论】:

    标签: mongodb mongoose mongodb-query aggregation-framework


    【解决方案1】:

    $group 管道阶段通过为_id 指定的“键”“分组”所有数据来工作。您实际聚合的其他字段与 _id 值是分开的,是它们自己的字段属性。

    所以你的$group 变成了这个:

    { "$group": {
        "_id": { "$hour": "$dt" },
        "price": { "$avg": "$price" }
    }}
    

    或者,如果您想按天打破,那么制作一个复合键:

    { "$group": {
        "_id": { 
            "day": { "$dayOfYear": "$dt" },
            "hour": { "$hour": "$dt" }
        },
        "price": { "$avg": "$price" }
    }}
    

    或者只是使用日期数学来生成按小时四舍五入的Date 对象:

    { "$group": {
        "_id": { 
            "$add": [
                { "$subtract": [
                    { "$subtract": [ "$dt", new Date(0) ] },
                    { "$mod": [
                        { "$subtract": [ "$dt", new Date(0) ] },
                        1000 * 60 *60
                    ]}
                ]},
                new Date(0)
             ]
        },
        "price": { "$avg": "$price" }
    }}
    

    从另一个日期对象中减去另一个日期对象(纪元日期)会产生一个数值,您可以使用应用的数学方法四舍五入(1000 毫秒、60 秒、60 分钟 = 1 小时),并将一个数字添加到日期对象会产生一个日期对应那个值。

    所以您的问题是您在 _id 中拥有所有内容,其中无法识别 $avg 累加器。所有累加器都需要在分组键之外指定。这就是意图。

    如果您想将累加器值作为分组键的一部分(虽然在这里似乎不相关),您可以跟随另一个分组阶段,引用从前者生成的字段。

    【讨论】:

    • 非常感谢,这正是我所需要的。就像在圣诞节的早晨醒来,圣诞老人爪仍然是真实的 :)
    • 你会看我的下一个问题吗?这是相同的查询,但我需要添加最常见的计数和平均值。 stackoverflow.com/questions/33708233/…
    猜你喜欢
    • 1970-01-01
    • 2021-05-05
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2021-12-15
    • 2014-04-17
    • 2016-07-26
    • 1970-01-01
    相关资源
    最近更新 更多