【发布时间】:2019-10-15 06:30:07
【问题描述】:
我使用 python 3.7.1(默认,2018 年 12 月 14 日,19:28:38)和 pymongo 3.7.2。
在 mongodb 中这有效:
db.collection.find(
{$and:[
{"field":{$regex:"bon?"}},
{"field":{$not:{$regex:"bon souple"}}},
{"field":{$not:{$regex:"bon léger"}}}
]}
)
所以在 pymongo 我做了同样的事情:
db.collection.find(
{"$and":[
{"field":{"$regex":"bon?"}},
{"field":{"$not":{"$regex":"bon souple"}}},
{"field":{"$not":{"$regex":"bon léger"}}}
]}
)
但它表示pymongo.errors.OperationFailure: $regex has to be a string。
所以我按照here的建议尝试了这个:
liste_reg=[
{'field': {'$regex': {'$not': re.compile('bon souple')}}},
{'field': {'$regex': {'$not': re.compile('bon léger')}}},
{'field': {'$regex': re.compile('bon?')}}
]
rslt=list(
db.collection.find({"$and":liste_reg})
)
我注意到即使没有特殊字符也表示相同的错误:
liste_reg=[
{'field': {'$regex': {'$not': re.compile('bon souple')}}} #where no special char is present
]
rslt=list(
db.collection.find({"$and":liste_reg})
)
所以我尝试使用"/" 作为:
liste_reg=[
{'field': {'$regex': {'$not':'/bon souple/'}}} #where no special char is present
#even tried re.compile('/bon souple/')
]
rslt=list(
db.collection.find({"$and":liste_reg})
)
同样的错误pymongo.errors.OperationFailure: $regex has to be a string 仍然出现。
我能做什么?
我对解决方案研究的一些更新
问题的核心似乎在于$not,因为当我这样做时:
liste_reg=[{'field': {'$regex': 'bon?'}}]
rslt=list(
db.collection.find({"$and":liste_reg})
)
len(rslt)#gives 23 013, what is ok.
没有错误。
一些示例
按照 Emma 的要求,我可以提供一个示例,它会在 mongo 中明确我的请求。 通常,我必须在现场使用这些方式:
- 秒
- très léger
- 莱热
- bon léger
- 好
- 便当
- 双人
- très 汤
- 整理
- 大声
- très Lourd
- 深刻
对我来说主要问题是我的蜘蛛没有正确解析,因为我没有为此编写足够强大的脚本。 我得到的不是仅仅“bon”,而是这样的结果:
{"_id":"ID1",
"field":"bon\r\n\t\t\t\t\t\t\t\t\r\n\t\t\t\t\t\t\t\r\n\t\t\t\t\t\t\t\r\n\t\t\t\t\t\t\t\t\r\n\t\t\t\t\t\t\t\t\t\r\n\t\t\t\t\t\t\t\t\t\tnon",
...}
这是许多其他错误解析之间的示例。
所以这就是为什么我想要以"bon?" 开头但不是"bon souple" 或"bon léger" 的结果,因为它们有正确的值,没有\n 或\t。
作为样本:
[{"_id":"ID1",
"field":"bon\r\n\t\t\t\t\t\t\t\t\r\n\t\t\t\t\t\t\t\r\n\t\t\t\t\t\t\t\r\n\t\t\t\t\t\t\t\t\r\n\t\t\t\t\t\t\t\t\t\r\n\t\t\t\t\t\t\t\t\t\tnon"},
{"_id":"ID2",
"field":"bon\r\n\t\t\t\t\t\t\t\t\r\n\t\t\t\t\t\t\t\r\n\t\t\t\t\t\t\t\r\n\t\t\t\t\t\t\r\n\t\t\t\t\t\tpremière"},
{"_id":"ID3",
"field":"bon\r\n\t\t\t\t\t\t\t\t\r\n\t\t\t\t\t\t\t\r\n\t\t\t\t\t\t\t\r\n\t\t\t\t\t\t\r\n\t\t\t\t\t\t2ème"},
{"_id":"ID4",
"field":"bon souple"},
{"_id":"ID5",
"field":"bon léger"}]
【问题讨论】:
-
@Emma 我用你所问的样本做了更新。或者至少我认为你问的是什么。
-
@Emma 正如您在演示中所说的那样,它可以在其中工作。但是,我无法解释为什么,当我在 robo3t
db.collection.find({"field":{$regex:"bon[^\s].+"}})的 mongo shell 中编写此代码时,出现的第一个文件是{ "_id" : "364714",..., "field" : "bon léger"}。我查看了查看文档,看看它是不是像"bon\t\t\t\t\nléger"这样的异常,实际上这真的是"bon léger"。在我的 mongo shell 中,它考虑了空格键。除了在 pymongo 中,我还获得了一个带有len(list(db.geny_rapp.find({'etat_terrain': {'$regex': "bon[^\s].+"}})))的空列表。 -
@Emma 老实说,我有另一种方法可以回答我的问题,但是没有正则表达式,这更复杂,我使用集合和集合上的操作:setA-setB -> 我想要的集合。但正如我所说,它更复杂,这不是目标。
标签: python regex python-3.x mongodb pymongo