MongoDB 中Aggregate使用与相关限制

本文涉及的产品
云数据库 MongoDB,独享型 2核8GB
推荐场景:
构建全方位客户视图
简介: MongoDB 中Aggregate使用与相关限制

MongoDB分组怎么用?

官网:https://docs.mongodb.com/manual/reference/operator/aggregation-pipeline/

不指定字段分组

案例1:


db.getCollection('6117Decartes').aggregate( 
   [
    { 
    $group : { 
        _id : null,
        "count":{$sum:1} } 
    } 
   ],
   {
        allowDiskUse: true
    } 
);


要注意的是,字段可被统计才行,否则会报错,看个例子。

代码 InstitutionID 是非统计字段


db.getCollection('6117Decartes').aggregate( 
   [
    { 
    $group : { 
        _id : null,
        "InstitutionID":"$InstitutionID"
        } 
    } 
   ],
   {
        allowDiskUse: true
    } 
);
正确的写法是:
db.getCollection('6117Decartes').aggregate(
   [
    {
    $group : {
        _id : null,
        "InstitutionID":{$max:"$InstitutionID"}
        }
    }
   ],
   {
        allowDiskUse: true
    }
);


否则报错如下:

640.png


案例2:

db.sales.insert([
    { "_id" : 1, "item" : "abc", "price" : 10, "quantity" : 2, "date" : ISODate("2014-03-01T08:00:00Z") },
    { "_id" : 2, "item" : "jkl", "price" : 20, "quantity" : 1, "date" : ISODate("2014-03-01T09:00:00Z") },
    { "_id" : 3, "item" : "xyz", "price" : 5, "quantity" : 10, "date" : ISODate("2014-03-15T09:00:00Z") },
    { "_id" : 4, "item" : "xyz", "price" : 5, "quantity" : 20, "date" : ISODate("2014-04-04T11:21:39.736Z") },
    { "_id" : 5, "item" : "abc", "price" : 10, "quantity" : 10, "date" : ISODate("2014-04-04T21:23:13.331Z") }
]);


不指定数据分组


db.sales.aggregate(
   [
      {
        $group : {
           _id : null,
           minPrice:{$min:"$price"},    //最小值
           maxPrice:{$max:"$price"},    //最大值
           avgPrice:{ $avg: "$price" }, //平均值
           totalPrice: { $sum: { $multiply: [ "$price", "$quantity" ] } }, //总价 $sum(price * quantity)
           lastItem:{$last:"$item"},    //取最后一条
           count: { $sum: 1 } // 总条目数
        }
      }
   ]
);


640.png



多字段分组


db.getCollection('6117Decartes').aggregate( 
   [
    { 
    $group : { 
        _id : {"InstitutionID":"$InstitutionID","logtype":"$logtype"},
        "总条目数":{$sum:1} } 
    } 
   ],
   {
        allowDiskUse: true
    } 
);


案例2:


db.sales.aggregate( 
   [
    { 
    $group : { 
        _id : {"商品":"$item", "价格":"$price"},
        "总条目数":{$sum:1} } 
    } 
   ] 
);


将 $push 聚合分组指定到列结构到数组中


db.books.insert([
    { "_id" : 8751, "title" : "The Banquet", "author" : "Dante", "copies" : 2 },
    { "_id" : 8752, "title" : "Divine Comedy", "author" : "Dante", "copies" : 1 },
    { "_id" : 8645, "title" : "Eclogues", "author" : "Dante", "copies" : 2 },
    { "_id" : 7000, "title" : "The Odyssey", "author" : "Homer", "copies" : 10 },
    { "_id" : 7020, "title" : "Iliad", "author" : "Homer", "copies" : 10 }
]);
db.books.aggregate(
   [
     { $group : { _id : "$author", books: { $push: "$title" } } }
   ]
);



可能出现的问题:分组内存使用超过限制时错误

{
"message" : "Exceeded memory limit for $group, but didn't allow external sort. Pass allowDiskUse:true to opt in.",
"stack" : "MongoError: Exceeded memory limit for $group, but didn't allow external sort. Pass allowDiskUse:true to opt in." +
              "at queryCallback (/tmp/.mount_nosqlbO7RhZG/app/resources/app.asar/node_modules/mongodb-core/lib/cursor.js:223:25)" +
              "at /tmp/.mount_nosqlbO7RhZG/app/resources/app.asar/node_modules/mongodb-core/lib/connection/pool.js:541:18" +
              "at _combinedTickCallback (internal/process/next_tick.js:131:7)" +
              "at process._tickCallback (internal/process/next_tick.js:180:9)",
"name" : "MongoError",
"ok" : 0,
"errmsg" : "Exceeded memory limit for $group, but didn't allow external sort. Pass allowDiskUse:true to opt in.",
"code" : 16945,
"codeName" : "Location16945"
}


怎么解决?

  • id 字段是必须要的,如果不指定字段进行分组则用 null,表示不分组的统计;
  • 分组内存使用限制是100M,默认情况下如果超过了限制100M则会出现错误。如果想对超过100M的大数据进行处理,可以使用 allowDiskUse 选项来进行分组时写到磁盘临时文件中处理。
db.getCollection('6117Decartes').aggregate( 
   [
    { 
    $group : { 
        _id : {"InstitutionID":"$InstitutionID","logtype":"$logtype"},
        "总条目数":{$sum:1} } 
    } 
   ],
   {
        allowDiskUse: true
    } 
);


相关实践学习
MongoDB数据库入门
MongoDB数据库入门实验。
快速掌握 MongoDB 数据库
本课程主要讲解MongoDB数据库的基本知识,包括MongoDB数据库的安装、配置、服务的启动、数据的CRUD操作函数使用、MongoDB索引的使用(唯一索引、地理索引、过期索引、全文索引等)、MapReduce操作实现、用户管理、Java对MongoDB的操作支持(基于2.x驱动与3.x驱动的完全讲解)。 通过学习此课程,读者将具备MongoDB数据库的开发能力,并且能够使用MongoDB进行项目开发。   相关的阿里云产品:云数据库 MongoDB版 云数据库MongoDB版支持ReplicaSet和Sharding两种部署架构,具备安全审计,时间点备份等多项企业能力。在互联网、物联网、游戏、金融等领域被广泛采用。 云数据库MongoDB版(ApsaraDB for MongoDB)完全兼容MongoDB协议,基于飞天分布式系统和高可靠存储引擎,提供多节点高可用架构、弹性扩容、容灾、备份回滚、性能优化等解决方案。 产品详情: https://www.aliyun.com/product/mongodb
相关文章
|
SQL NoSQL Unix
13 MongoDB高级 - 聚合 aggregate
13 MongoDB高级 - 聚合 aggregate
69 0
|
SQL NoSQL Unix
MongoDB 聚合aggregate
MongoDB 聚合aggregate
137 0
|
NoSQL MongoDB
MongoDB aggregate聚合分组查询
MongoDB aggregate聚合分组查询
306 0
|
存储 NoSQL Java
MongoDB:17-MongoDB-索引限制及其他限制规则
MongoDB:17-MongoDB-索引限制及其他限制规则
909 0
|
NoSQL MongoDB 索引
mongodb的限制
知道一个产品的限制所在,就可以更好的使用它。目前已知的mongodb限制如下: BSON Document Size:最大为16M 数据库:大小写敏感、数据库名称必须少于64个字符 集合名称不能包含如下信息:contain the $.
2302 0