• mongoose聚合——$group


    $group:将集合中的文档分组

    数据表

    //Students
    [{"_id":"60adff66e57f4255b4c7e19a", "name":"唐戚", "student_id":232323, "class_oid":"60adff65e57f4255b4c7e194", "come_year":"2020-01-01T00:00:00.000Z", "grade":{"math":37,"chinese":98,"english":71}, "__v":0 } .....省略16条 {"_id":"60ae02937e294b5894229d70", "name":"安俞", "student_id":232328, "class_oid":"60adff65e57f4255b4c7e199", "come_year":"2021-01-01T00:00:00.000Z", "grade":{"math":29,"chinese":39,"english":79}, "__v":0 }]

    代码

    示例中只给出aggregate中的参数,文末给出完整代码

    1.通过某个字段分组

    这里使用come_year分组,数据中有两个年份,2020和2021,$group是通过_id来分组。

    聚合参数:

     const query=[
        {
          $group:{
            _id:'$come_year'
          }
        }
      ]

    结果:

    [
      { _id: 2020-01-01T00:00:00.000Z },
      { _id: 2021-01-01T00:00:00.000Z }
    ]

    2.数学运算

    找出在2020年和2021年入学学生中各科成绩最高分,最低分,平均分
    使用:$max:该分组中最大值
    $min:该分组中最小值
    $avg:该分组的平均值
    $sum:计算总和,$sum:1表示返回总和的1倍
    const query=[
        {
          $group:{
            _id:'$come_year',
            maxEnglish:{$max:'$grade.english'},
            minEnglish:{$min:'$grade.english'},
            avgEnglish:{$avg:'$grade.english'},
            total:{$sum:1}
          }
        }
      ]

    结果:

    [
      {
        _id: 2020-01-01T00:00:00.000Z,
        maxEnglish: 74,
        minEnglish: 5,
        avgEnglish: 42.25,
        total: 12
      },
      {
        _id: 2021-01-01T00:00:00.000Z,
        maxEnglish: 84,
        minEnglish: 39,
        avgEnglish: 63.666666666666664,
        total: 6
      }
    ]

    3.在分组中插入字段

    获得不同学年有哪些学生,给出姓名

    使用$addToSet:在结果文档中插入一个数组

    const query=[
        {
          $group:{
            _id:'$come_year',
            test:{$addToSet:'$name'}
          }
        }
      ]

    结果:

    [
      {
        _id: 2020-01-01T00:00:00.000Z,
        test: [
          '凤殷', '吴于', '韩马',
          '尤郝', '喻蒋', '曹罗',
          '钱许', '唐戚', '卜严',
          '谢柳', '薛金', '俞彭'
        ]
      },
      {
        _id: 2021-01-01T00:00:00.000Z,
        test: [ '花唐', '酆史', '朱吴', '平殷', '安俞', '邹尤' ]
      }
    ]

    4.计算文档总数

    计算有多少学生

    可以将_id设为null,就不分组

    const query=[
        {
          $group:{
            _id:null,
            total:{$sum:1}
          }
        }
      ]

    结果:

    [ { _id: null, total: 18 } ]

    5.插入新增字段

    获取不同学年学生信息

    使用$push:在结果文档中插入值到数组中,和addToSet不同的是,$push要创建副本

    const query=[
        {
          $group:{
            _id:'$come_year',
            students:{
              $push:{
                _id:'$_id',
                name:'$name',
                grade:'$grade'
              }
            }
          }
        }
      ]

    结果:

    [
      {
        _id: 2020-01-01T00:00:00.000Z,
        students: [
          [Object], [Object],
          [Object], [Object],
          [Object], [Object],
          [Object], [Object],
          [Object], [Object],
          [Object], [Object]
        ]
      },
      {
        _id: 2021-01-01T00:00:00.000Z,
        students: [ [Object], [Object], [Object], [Object], [Object], [Object] ]
      }
    ]

    完整代码

    const Articles = require('../../model/articles');
    const Users = require('../../model/users');
    var Departments=require('../../model/departments');
    var Students=require('../../model/students');
    var Classes=require('../../model/classes');
    
    //$group:将集合中的文档分组
    //语法:{ $group: { _id: <expression>, <field1>: { <accumulator1> : <expression1> }, ... } }
    
    //---------------------------------1-----------------
    //按照入学日期分组
    /*
    [
      { _id: 2020-01-01T00:00:00.000Z },
      { _id: 2021-01-01T00:00:00.000Z }
    ] */
    async function group1(){
      const query=[
        {
          $group:{
            _id:'$come_year'
          }
        }
      ]
    
      await studentsAggregate([...query])
    }
    
    
    //----------------2----------------
    //找出在2020年和2021年入学学生中各科成绩最高分,最低分,平均分
    /**
     * [
      {
        _id: 2020-01-01T00:00:00.000Z,
        maxEnglish: 74,
        minEnglish: 5,
        avgEnglish: 42.25,
        total: 12
      },
      {
        _id: 2021-01-01T00:00:00.000Z,
        maxEnglish: 84,
        minEnglish: 39,
        avgEnglish: 63.666666666666664,
        total: 6
      }
    ]
     */
    async function group2(){
      const query=[
        {
          $group:{
            _id:'$come_year',
            maxEnglish:{$max:'$grade.english'},
            minEnglish:{$min:'$grade.english'},
            avgEnglish:{$avg:'$grade.english'},
            total:{$sum:1}
          }
        }
      ]
    
      await studentsAggregate([...query])
    }
    
    //------------------3----------------
    //插入数组到分组中
    /*
    [
      {
        _id: 2020-01-01T00:00:00.000Z,
        test: [
          '凤殷', '吴于', '韩马',
          '尤郝', '喻蒋', '曹罗',
          '钱许', '唐戚', '卜严',
          '谢柳', '薛金', '俞彭'
        ]
      },
      {
        _id: 2021-01-01T00:00:00.000Z,
        test: [ '花唐', '酆史', '朱吴', '平殷', '安俞', '邹尤' ]
      }
    ]
    */
    async function group3(){
      const query=[
        {
          $group:{
            _id:'$come_year',
            test:{$addToSet:'$name'}
          }
        }
      ]
    
      await studentsAggregate([...query])
    }
    
    //---------------4------------
    //常用计算总数
    //[ { _id: null, total: 18 } ]
    async function group4(){
      const query=[
        {
          $group:{
            _id:null,
            total:{$sum:1}
          }
        }
      ]
    
      await studentsAggregate([...query])
    }
    
    //----------------------5---------------
    //获取不同学年的学生信息
    async function group5(){
      const query=[
        {
          $group:{
            _id:'$come_year',
            students:{
              $push:{
                _id:'$_id',
                name:'$name',
                grade:'$grade'
              }
            }
          }
        }
      ]
    
      await studentsAggregate([...query])
    }
    
    
    /**
     * articles聚合结果模板
     * @param {Array} query 聚合的参数
     */
     async function studentsAggregate(query) {
      try {
        const result = await Students.aggregate([
          ...query
        ])
    
        console.log(result);
    
      } catch (err) {
        console.log((query))
        console.log("聚合失败...", err)
      }
    }
    
    
    function main(){
      group5();
    }
    
    main();
  • 相关阅读:
    Webpack配置
    闭包函数
    Vue2.0(一) 新手搭建环境
    用python编写一个合格的ftp程序,思路是怎样的?
    项目流程规范
    python: 基本数据类型 与 内置函数 知识整理
    前端知识 备忘录
    架构的演化路线
    深入理解并使用python的模块与包
    jquery 知识整理
  • 原文地址:https://www.cnblogs.com/ellen-mylife/p/14814273.html
Copyright © 2020-2023  润新知