我有一个带字段的mongo集合 visit_id,user_id,date,action 1,action 2
example: 1 u100 2012-01-01 phone-call - 2 u100 2012-01-02 - computer-check
我是否可以将mongodb用户同时进行电话呼叫和计算机检查? (基本上它是不同行上的AND)
答案 0 :(得分:1)
我想如果没有map / reduce工作就不可能。
我看到它可以通过以下方式完成:
1.首先你需要运行map / reduce产生的结果如下:
{
_id : "u100",
value: {
actions: [
"phone-call",
"computer-check",
"etc..."
]
}
}
2.然后您可以通过elemMatch
查询上述m / r结果答案 1 :(得分:1)
您无法通过单个查询执行此操作 - 如果这是您在应用程序中经常执行的操作,我不建议使用map / reduce - 我建议您使用mongodb进行查询$或运算符,然后在客户端上处理它以获得一组唯一的user_id。
例如:
db.users.find({$or:[{"action 1":"phone-call"}, {"action 2":"computer-check"}]})
将来,您应该以不同的格式保存您的数据,如上面Andrew建议的那样。
答案 2 :(得分:0)
可以使用MongoDB group
method查询,与SQL group by
运算符相比。
我没有对此进行测试,但您的查询可能类似于:
var results = db.coll.group({
key: { user_id: true },
cond: { $or: [ { action1: "phone-call" }, { action2: "computer-check" } ] },
initial: { actionFlags: 0 },
reduce: function(obj, prev) {
if(obj.action1 == "phone-call") { prev.actionFlags |= 1; }
if(obj.action2 == "computer-check") { prev.actionFlags |= 2; }
},
finalize: function(doc) {
if(doc.actionFlags == 3) { return doc; }
return null;
}
});
同样,我没有对此进行测试,这是基于我对文档的阅读。您按user_id
(key
声明)进行分组。您要通过的行包含action1 == "phone-call"
或action2 == "computer-check"
(cond
声明)。开始检查特定user_id
时的初始状态为0(initial
)。对于每一行,您检查action1 == "phone-call"
是否设置其标志,然后选中action2 == "computer-check"
并设置它的标志(reduce
功能)。标记行类型后,检查以确保两个标志都已设置。如果是,请保留对象,否则将其删除(finalize
函数)。
最后一部分是我唯一不确定的部分,因为文档没有明确说明你可以删除finalize
函数中的记录。我可能需要更多的时间来设置一些测试数据,而不是让你看看上面的例子是否有效。