As follows:
After filtering, they are grouped again, and the two fields are grouping conditions.
However, I just want to get the time within the group, that is, the data with fdate being the largest.
How can it be done? ?
db.SEC_2018_05_12.aggregate([{ $match : { fyear : { $eq : 2018},fmonth:{$eq : 5},fday:{$eq : 12},fhour:{$eq : 17},fmin:{$eq : 8} } }
, { $group: { _id: {dev_id: "$dev_id", data_id: "$data_id"},maxTimeValue: { $max: "$fdate" } } } ]).pretty()
If you can give some test conditions, it will be easier for others to understand your problem.
First of all, $eq, this operator is unnecessary to write most of the time. So your query is equivalent to:db.SEC_2018_05_12.aggregate([ { $match : { fyear : 2018, fmonth: 5, fday: 12, fhour: 17, fmin: 8 } }, { $group: { _id: {dev_id: "$dev_id", data_id: "$data_id"}, maxTimeValue: { $max: "$fdate" } } } ]).pretty()
Then your request is to get the first data, not just the largest one.
fdate
Value. You can change your mind to understand this problem:Sort by dev_id asc, data_id asc, fdate desc, and then take the first piece of data from each grouping.
According to this idea, the query should be:
db.SEC_2018_05_12.aggregate([ { $match : { fyear : 2018, fmonth: 5, fday: 12, fhour: 17, fmin: 8 } }, { $sort: { dev_id: 1, data_id: 1, fdate: -1} }, { $group: { _id: {dev_id: "$dev_id", data_id: "$data_id"}, maxDoc: { $first: "$$ROOT" } } } ]).pretty()
Finally, I would like to talk about the problem of data model design.
$match
This is actually a time, but it has been split into many parts to store. Unless there are clear reasons to support it, individuals are not very much in favor of such an approach.
- Originally there was only 4 bytes at a time, so you became 5 x 4 = 20 bytes. Pay attention to the storage space.
$match
/$sort
Need index support, so the original index will now become a joint index of 5 fields, which is also a waste of space and efficiency.In the case of large amount of data, the above query needs index support. In your current writing style, the index should read:
{ fyear: 1, fmonth: 1, fday: 1, fhour: 1, fmin: 1, dev_id: 1, data_id: 1, fdate: -1 }
It looks scary enough, doesn’t it? But in fact, the previous pile of time itself is only one time.