我有一个用户,在里面我保留了他评价的项目列表。
> db.users.findOne()
{
"_id" : ObjectId("5321985944aebf2ca6f2075f"),
"ratings" : [
{
"532192d344aebf2ca6f2075e" : 0
},
{
"532199d144aebf2ca6f20760" : 1
}
],
"email" : "joe@example.com",
"name" : "Joe Bloggs"
}
评级的格式如下:
{ item_id : <score> }
问题是,如果用户将同一项目评级两次(评级不同),而不是替换旧项目,则会将新元素添加到数组中。
我使用$addToSet
来避免重复,但我想替换旧的评级。
我目前正以复杂的方式做这件事,有什么比这更简单了吗? (我使用的是Java,但如果解决方案没有,则无关紧要。)
答案 0 :(得分:0)
你不应该使用$set吗?
db.users.update({"email":"joe@example.com"}, {$set:{"ratings.item_id":5}})
这样,如果没有早期评级,则会添加一个新评级。如果已经存在,则会更新。
注意:您需要更换&#34; item_id&#34;使用客户的实际商品ID。
答案 1 :(得分:0)
由于多种原因,这可能不是最好的架构设计。你会得到更好的服务:
{
"_id" : ObjectId("5321985944aebf2ca6f2075f"),
"ratings" : [
{
id: "532192d344aebf2ca6f2075e", score: 0
},
{
id: "532199d144aebf2ca6f20760", score: 1
}
],
"email" : "joe@example.com",
"name" : "Joe Bloggs"
}
至少以这种方式,您可以匹配数组元素的id
。
虽然你的问题。 $addToSet是一个很好的方便,但当然不能解决你的问题。它仍然可以使用,但是如果你想添加到&#34;得分&#34;像这样你必须使用(当然是新模型):
var count = db.collection.find({
"_id" : ObjectId("5321985944aebf2ca6f2075f"),
"ratings.id": "532192d344aebf2ca6f2075e"
}).count();
if ( count != 0 ) {
db.collection.update(
{
"_id" : ObjectId("5321985944aebf2ca6f2075f"),
"ratings.id": "532192d344aebf2ca6f2075e"
},
{
"$inc": { "ratings.$.score": 1 }
}
);
} else {
db.collection.update(
{
"_id" : ObjectId("5321985944aebf2ca6f2075f"),
"ratings.id": "532192d344aebf2ca6f2075e"
},
{
"$push": {
"id": newId,
"score": newScore
}
}
);
}
或者您的实施语言中的任何等效内容。
因此,$addToSet在您的情况下变得有点多余,因为您需要检查以确定您是$set还是$inc。更多参与,但它是唯一的方法。