在monggodb聚合操作中有时会对数组对象中的数据求和
$unwind 会把数组中的数据分多条数据,数组外公共数据相同
{'_id': ObjectId('61a783dd74e4719e37f6e84e'), 'name': 'dahai', 'data': [{'k1_name': '语文', 'score': 78}, {'k2_name': '数学', 'score': 90}, {'k3_name': '英语', 'score': 80}]}
$unwind后会变成三条数据
{'_id': ObjectId('61a783dd74e4719e37f6e84e'), 'name': 'dahai', 'data': {'k1_name': '语文', 'score': 78}} {'_id': ObjectId('61a783dd74e4719e37f6e84e'), 'name': 'dahai', 'data': {'k2_name': '数学', 'score': 90}} {'_id': ObjectId('61a783dd74e4719e37f6e84e'), 'name': 'dahai', 'data': {'k3_name': '英语', 'score': 80}}
然后下按name分组data.score求和就可以了
测试代码如何:
import pymongo
client = pymongo.MongoClient(f"mongodb://root:root@172.16.1.17:27017")
db = client.test
data = [{
"name": "dahai",
"data": [{"k1_name": "语文", "score": 78}, {"k2_name": "数学", "score": 90}, {"k3_name": "英语", "score": 80}]
},
{
"name": "小明",
"data": [{"k1_name": "语文", "score": 89}, {"k2_name": "数学", "score": 99}, {"k3_name": "英语", "score": 80}]
}
]
# cur = db.user.insert_many(data)
rows = db.user.find()
for row in rows:
print(row)
print("\n")
rows = db.user.aggregate([{"$match": {}},
{"$unwind": "$data"}
])
for row in rows:
print(row)
print("\n")
rows = db.user.aggregate([{"$match": {}},
{"$unwind": "$data"},
{"$group": {"_id": "$name", "total_score": {"$sum": "$data.score"}}}
])
for row in rows:
print(row)
输出如下:
{'_id': ObjectId('61a783dd74e4719e37f6e84e'), 'name': 'dahai', 'data': [{'k1_name': '语文', 'score': 78}, {'k2_name': '数学', 'score': 90}, {'k3_name': '英语', 'score': 80}]} {'_id': ObjectId('61a783dd74e4719e37f6e84f'), 'name': '小明', 'data': [{'k1_name': '语文', 'score': 89}, {'k2_name': '数学', 'score': 99}, {'k3_name': '英语', 'score': 80}]}
{'_id': ObjectId('61a783dd74e4719e37f6e84e'), 'name': 'dahai', 'data': {'k1_name': '语文', 'score': 78}} {'_id': ObjectId('61a783dd74e4719e37f6e84e'), 'name': 'dahai', 'data': {'k2_name': '数学', 'score': 90}} {'_id': ObjectId('61a783dd74e4719e37f6e84e'), 'name': 'dahai', 'data': {'k3_name': '英语', 'score': 80}} {'_id': ObjectId('61a783dd74e4719e37f6e84f'), 'name': '小明', 'data': {'k1_name': '语文', 'score': 89}} {'_id': ObjectId('61a783dd74e4719e37f6e84f'), 'name': '小明', 'data': {'k2_name': '数学', 'score': 99}} {'_id': ObjectId('61a783dd74e4719e37f6e84f'), 'name': '小明', 'data': {'k3_name': '英语', 'score': 80}}
{'_id': '小明', 'total_score': 268} {'_id': 'dahai', 'total_score': 248}
?
|