MongoDB聚合中能否拼接两个DBRef?及交易数据统计需求
嘿,我来帮你搞定这个MongoDB聚合统计的问题,顺便解答你关于DBRef拼接的疑问~
一、完成聚合统计的完整语句
要统计唯一买家数、卖家数,以及买家+卖家的唯一组合数,我们可以通过一次聚合操作完成,具体语句如下:
db.getCollection('transactions').aggregate([ // 提取买家、卖家的ID,并生成买卖组合标识 { $addFields: { buyerId: "$buyer.$id", sellerId: "$seller.$id", // 将两个ID转成字符串后拼接成唯一组合键 buyerSellerPair: { $concat: [ { $toString: "$buyer.$id" }, "|", { $toString: "$seller.$id" } ] } } }, // 分组收集所有唯一的买家、卖家和组合 { $group: { _id: null, uniqueBuyers: { $addToSet: "$buyerId" }, uniqueSellers: { $addToSet: "$sellerId" }, uniquePairs: { $addToSet: "$buyerSellerPair" } } }, // 计算各类唯一值的数量 { $project: { _id: 0, uniqueBuyerCount: { $size: "$uniqueBuyers" }, uniqueSellerCount: { $size: "$uniqueSellers" }, uniquePairCount: { $size: "$uniquePairs" } } } ])
语句说明:
$addFields阶段:先从DBRef中提取$id字段(直接用整个DBRef对象做去重的话,会包含$ref字段,而我们只需要ID的唯一性),同时用$toString把ObjectId转成字符串,再通过$concat拼接成唯一的买卖组合键。$group阶段:以_id: null进行全局分组,用$addToSet收集所有不重复的买家ID、卖家ID和组合键。$project阶段:用$size计算每个集合的长度,得到我们需要的统计数。
另外,如果你觉得字符串拼接麻烦,也可以用数组来表示买卖组合,这样不需要转字符串,同样能识别唯一组合:
// 修改$addFields里的组合键生成方式 buyerSellerPair: ["$buyer.$id", "$seller.$id"]
这种方式下,只有当买家ID和卖家ID完全相同时,才会被视为同一个组合,统计结果是准确的。
二、关于MongoDB聚合中用$concat拼接DBRef的问题
直接对整个DBRef对象使用$concat是不行的——因为$concat只能接收字符串类型的参数,而DBRef是一个包含$ref和$id的嵌套对象。
但我们可以先提取DBRef中的$id字段(ObjectId类型),通过$toString将其转换为字符串后,再使用$concat进行拼接,就像上面聚合语句里的做法。这样就能实现两个DBRef对应ID的拼接啦。
内容的提问来源于stack exchange,提问作者Bill
相关产品推荐
相关产品推荐

