我已经提供了一个名为votes
的集合,其中包含基于此设计的文档:
{
"_id" : ObjectId("56c000000000000001"),
"timestamp" : 1456441690,
"filename" : "42598295724057245724579",
"phoneNumber" : 49123456789,
"phoneNumberVotes" : [
49123456783,
49123456784
]
}
phoneNumberVotes
数组可以为空。
我正在尝试执行此查询:
db.getCollection('votes').find
(
{
$and:[
{ phoneNumber: { $ne: 49123456789}},
{ phoneNumber: { $nin: phoneNumberVotes }}
]
},
{ timestamp: 1, filename: 1, phoneNumber: 1, phoneNumberVotes: 1}
)
但这不起作用。当我尝试在查询中“手动”创建一个数组时,它可以工作,例如:
db.getCollection('votes').find
(
{
$and:[
{ phoneNumber: { $ne: 49123456789}},
{ phoneNumber: { $nin: [49123456783,49123456784] }}
]
},
{ timestamp: 1, filename: 1, phoneNumber: 1, phoneNumberVotes: 1}
)
我尝试使用的方法有什么问题?谢谢你的帮助!
答案 0 :(得分:2)
您无法直接比较字段。 Documentation中的<field>
和<value>
之间存在差异。
在您的情况下,您需要使用$where
运算符来执行javascript:
db.votes.find
(
{
phoneNumberVotes:{$exists:true},
phoneNumber:{$exists:true, $ne:"49123456789"},
$where: 'this.phoneNumberVotes.indexOf(this.phoneNumber) < 0'
},
{ timestamp: 1, filename: 1, phoneNumber: 1, phoneNumberVotes: 1}
)
它适用于标量值。
您正在使用NumberLong的数字。有一个old bug与对象比较相关,因此您需要将电话号码转换为字符串:
db.votes.find
(
{
phoneNumberVotes:{$exists:true},
phoneNumber:{$exists:true, $ne:49123456789},
$where: 'this.phoneNumberVotes.map(function(n){return n + ""}).indexOf(this.phoneNumber + "") < 0'
},
{ timestamp: 1, filename: 1, phoneNumber: 1, phoneNumberVotes: 1}
)
它可能很慢,因此将电话号码转换为数据库中的字符串可能是值得的,而不是运行时。