我认为这是一个很好的问题和答案,所以我决定在Java中使用Spring Data与MongoDB解决此问题。要阿霞的回答转换成Java mongodb的代码,我做了以下内容:
public void commentTest() {
BasicDBObject o1 = new BasicDBObject();
o1.append("c", "$commentor");
o1.append("i", "$commentid");
Aggregation aggCount = newAggregation(
project("commentid", "commentor")
.andExpression("concat(\"$strip\",\"-\",\"$yy\",\"/\",\"$mo\",\"/\",\"$da\")").as("strip"),
group("strip").push(o1).as("comms").max("commentid").as("max"),
match(Criteria.where("comms.c").is("Simon")),
unwind("comms"),
match(Criteria.where("comms.c").is("Simon")));
logger.info(aggCount.toString());
AggregationResults<CommentTest> groupCount = mongoTemplate.aggregate(aggCount, "commenttest", CommentTest.class);
List<CommentTest> resultCount = groupCount.getMappedResults();
ObjectMapper mapper = new ObjectMapper();
try {
logger.info(mapper.writeValueAsString(resultCount));
} catch (IOException e) {
e.printStackTrace();
}
}
然后让mongotemplate成功解析结果为CommentTest
类,我不得不创建minicks结果类:
Document(collection = "commenttest")
@JsonInclude(JsonInclude.Include.NON_NULL)
public class CommentTest {
private String id, body, commentid, commentor, commentorid, da, filename, mo, strip, stripname, time, yy, max;
@JsonProperty
private comms comms;
public CommentTest.comms getComms() {
return comms;
}
public void setComms(CommentTest.comms comms) {
this.comms = comms;
}
public static class comms implements Serializable {
private String c,i;
public String getC() {
return c;
}
public void setC(String c) {
this.c = c;
}
public String getI() {
return i;
}
public void setI(String i) {
this.i = i;
}
}
public String getId() {
return id;
}
public void setId(String id) {
this.id = id;
}
public String getBody() {
return body;
}
public void setBody(String body) {
this.body = body;
}
public String getCommentid() {
return commentid;
}
public void setCommentid(String commentid) {
this.commentid = commentid;
}
public String getCommentor() {
return commentor;
}
public void setCommentor(String commentor) {
this.commentor = commentor;
}
public String getCommentorid() {
return commentorid;
}
public void setCommentorid(String commentorid) {
this.commentorid = commentorid;
}
public String getDa() {
return da;
}
public void setDa(String da) {
this.da = da;
}
public String getFilename() {
return filename;
}
public void setFilename(String filename) {
this.filename = filename;
}
public String getMo() {
return mo;
}
public void setMo(String mo) {
this.mo = mo;
}
public String getStrip() {
return strip;
}
public void setStrip(String strip) {
this.strip = strip;
}
public String getStripname() {
return stripname;
}
public void setStripname(String stripname) {
this.stripname = stripname;
}
public String getTime() {
return time;
}
public void setTime(String time) {
this.time = time;
}
public String getYy() {
return yy;
}
public void setYy(String yy) {
this.yy = yy;
}
public String getMax() {
return max;
}
public void setMax(String max) {
this.max = max;
}
}
我然后通过插入这些4个模拟条目创建MongoDB中一些测试数据:
{ "_id" : ObjectId("518f14e5394594efbe18068c"), "body" : "1", "commentid" : "2525923", "commentor" : "Simon", "commentorid" : "769338", "da" : "25", "filename" : "/mnt/sshfs/gocomics/comments/100.out.bz2", "mo" : "11", "strip" : "luann", "stripname" : "Luann", "time" : "1 day ago", "yy" : "2011" }
{ "_id" : ObjectId("518f14e5394594efbe18068d"), "body" : "2", "commentid" : "2525924", "commentor" : "Josh", "commentorid" : "769339", "da" : "25", "filename" : "/mnt/sshfs/gocomics/comments/100.out.bz2", "mo" : "11", "strip" : "luann", "stripname" : "Luann", "time" : "1 day ago", "yy" : "2011" }
{ "_id" : ObjectId("518f14e5394594efbe18068e"), "body" : "3", "commentid" : "2525925", "commentor" : "Peter", "commentorid" : "769340", "da" : "25", "filename" : "/mnt/sshfs/gocomics/comments/100.out.bz2", "mo" : "11", "strip" : "luann", "stripname" : "Luann", "time" : "1 day ago", "yy" : "2011" }
{ "_id" : ObjectId("518f14e5394594efbe18068f"), "body" : "old1", "commentid" : "2525905", "commentor" : "Peter", "commentorid" : "769340", "da" : "24", "filename" : "/mnt/sshfs/gocomics/comments/100.out.bz2", "mo" : "11", "strip" : "luann", "stripname" : "Luann", "time" : "1 day ago", "yy" : "2011" }
我然后跑的代码和这里的结果:
[{"id":"luann-2011/11/25","max":"2525925","comms":{"c":"Simon","i":"2525923"}}]
结果可以解释为后luann-2011/11/25
具有最大评论数(或蒙戈ID)为2525925
,而您的评论有2525923
的ID。因此,您有评论后有评论,因此您需要获取新的评论。你需要编写你的逻辑编程。
您没有注释中特定条的唯一标识符?只是带yy-mo-da的组合? (我猜文件名是一个唯一的标识符,但它似乎hacky)... – 2013-05-12 19:27:14
不,我不知道,但我想我可以创建一个(文件名不唯一,每个文件名有20个评论)。 MongoDB的多字段索引是否有问题?会创建一个“strip-yy-mo-da”字段帮助吗?我假设MongoDB没有意见和/或创建“strip-yy-mo-da”作为虚拟字段不会有帮助? – barrycarter 2013-05-12 19:33:14
看到我的答案 - 第一个项目阶段只是将名称合并到唯一的条形标识符中,主要是为了进一步简化语法。只是想知道没有带yy-mm-dd类型的场的原因是什么。并不一定是唯一的 - 对这些类型的模式来说,分箱是一个很好的答案。 – 2013-05-12 20:16:29