rmongodb:在查询中使用 $or
Posted
技术标签:
【中文标题】rmongodb:在查询中使用 $or【英文标题】:rmongodb: using $or in query 【发布时间】:2012-08-22 05:51:34 【问题描述】:我正在努力在 R 和 rmongodb 中使用 $or 创建查询。我想效仿的是 cmdline mongo:
db.people.find( $or : [ "person.cell": $exists : true , "person.home": $exists : true ] )
我想提取 person.cell 不为 null 或 person.home 不为 null 的记录。我可以单独查询每个,但是当我在 rmongodb 中使用 $or 创建缓冲区时无法取回数据,使用 rmongodb 的 R 代码如下所示:
l <- list("$exists"="true")
buf <- mongo.bson.buffer.create()
mongo.bson.buffer.start.array(buf, "$or")
mongo.bson.buffer.append.list(buf, "person.cell", l)
mongo.bson.buffer.append.list(buf, "person.home", l)
mongo.bson.buffer.finish.object(buf)
b <- mongo.bson.from.buffer(buf)
mongo.find(mongo, "work.people", b)
返回没有记录,没有错误,只是一个空集。正如我所提到的,我可以在 person.cell 或 person.home 上进行查找并获得结果,但当我尝试执行 $or(在 rmongodb 中)以便我使用 person.cell 或 person.home 提取记录时却不行.
我也试过这个:
buf <- mongo.bson.buffer.create()
mongo.bson.buffer.start.array(buf, "$or")
mongo.bson.buffer.start.object(buf, "person.cell")
mongo.bson.buffer.append(buf, "$exists", "true")
mongo.bson.buffer.finish.object(buf)
mongo.bson.buffer.start.object(buf, "person.home")
mongo.bson.buffer.append(buf, "$exists", "true")
mongo.bson.buffer.finish.object(buf)
mongo.bson.buffer.finish.object(buf)
b <- mongo.bson.from.buffer(buf)
mongo.find(mongo, "work.people", b)
但是我得到了相同的空集结果(当我查看它时,“b”看起来相同)。我被这个卡住了。
【问题讨论】:
【参考方案1】:您创建 mongo bson 数组的方式是错误的。您缺少零件
mongo.bson.buffer.start.object(buf, "0")
...
mongo.bson.buffer.finish.object(buf)
mongo.bson.buffer.start.object(buf, "1")
...
mongo.bson.buffer.finish.object(buf)
有关工作示例,请查看有关以下内容的最新评论: https://github.com/mongosoup/rmongodb/issues/17
我希望这暂时有效。
所有 .to.list / .from.list / .append.list 命令都有一个错误。我正在研究一个更简单的解决方案!
【讨论】:
【参考方案2】:bson <- mongo.bson.from.JSON(' "$or" : [ "person.cell": "$exists" : true , "person.home": "$exists" : true ] ')
mongo.find(mongo, "work.people", bson)
【讨论】:
【参考方案3】:为了避免编写 mongo.bson.buffer-statements 的序列,我编写了一个包 (rmongodbHelper),它将 JSON 或 list() 转换为 BSON 对象,然后可以与 rmongodb 一起使用。
首先让我们设置环境:
library(rmongodb)
# install rmongodbHelper package from GitHub
library(devtools)
devtools::install_github("joyofdata/rmongodbHelper")
library(rmongodbHelper)
# the MongoDB instance
ns <- "dbx.collx"
M <- mongo.create()
mongo.is.connected(M)
mongo.remove(M, ns, json_to_bson(""))
# inserting a number of dummy objects
# JSON keys currently are expected to be wrapped in double quotes!
objs <- c(
'"_id":-1',
'"_id":-2, "person":',
'"_id":-3, "person":"x":0',
'"_id":1, "person":"cell":0',
'"_id":2, "person":"home":0',
'"_id":3, "person":"cell":0,"home":0'
)
for(obj in objs)
mongo.insert(M, ns, json_to_bson(obj))
让我们通过 MongoDB shell 看看它们是否插入成功:
> use dbx
switched to db dbx
> db.collx.find().pretty()
"_id" : -1
"_id" : -2, "person" :
"_id" : -3, "person" : "x" : 0
"_id" : 1, "person" : "cell" : 0
"_id" : 2, "person" : "home" : 0
"_id" : 3, "person" : "cell" : 0, "home" : 0
现在让我们用查询来搜索文档:
# searching for those objects
# JSON keys currently are expected to be wrapped in double quotes!
json_qry <-
'
"$or" : [
"person.cell": "$exists" : true ,
"person.home": "$exists" : true
]
'
cur <- mongo.find(M, "dbx.collx", json_to_bson(json_qry))
while(mongo.cursor.next(cur))
print(mongo.cursor.value(cur))
这就是我们最终得到的结果:
_id : 1 1.000000
person : 3
cell : 1 0.000000
_id : 1 2.000000
person : 3
home : 1 0.000000
_id : 1 3.000000
person : 3
cell : 1 0.000000
home : 1 0.000000
【讨论】:
【参考方案4】:我发现这个查询在RMongo 中更容易解决:
mongo <- mongoDbConnect(dbName="work", host="localhost",port='27017')
result <- dbGetQuery(mongo, "people","
'$or': [
'person.cell':'$exists':true,
'person.home':'$exists':true
]"
)
结果将是data.frame
。
【讨论】:
以上是关于rmongodb:在查询中使用 $or的主要内容,如果未能解决你的问题,请参考以下文章