Javascript MongoDB在自由文本搜索列表中检查多个正则表达式匹配

Javascript MongoDB在自由文本搜索列表中检查多个正则表达式匹配,javascript,search,node.js,mongodb,Javascript,Search,Node.js,Mongodb,我正在设置一个mongoDB,以允许按照建议使用多键进行(简单的)关键字搜索。记录看起来也很相似: { title: { title: "A river runs through", _keywords: ["a","river","runs","through"] ) , ... } 我使用nodejs服务器端,所以我使用javascript。以下查询将匹配(这是在mongo终端中运行的): 但是,这些并不是: > db.torrents_sorted.find({'title._ke

我正在设置一个mongoDB,以允许按照建议使用多键进行(简单的)关键字搜索。记录看起来也很相似:

{ title: { title: "A river runs through", _keywords: ["a","river","runs","through"] ) , ... }
我使用nodejs服务器端,所以我使用javascript。以下查询将匹配(这是在mongo终端中运行的):

但是,这些并不是:

> db.torrents_sorted.find({'title._keywords' : {"$all" : ["/river/i","/the/i"]} }).count()
0

> db.torrents_sorted.find({'title._keywords' : {"$all" : [{ "$regex" : "river", "$options" : "i" },{ "$regex" : "the", "$options" : "i" }]} }).count()
0
使用单个正则表达式(不使用$and或$all)不匹配:

db.torrents_sorted.find({'title._keywords':{“$regex”:“river”,“$options”:“i”}).count() 1461

有趣的是,使用python和pymongo编译正则表达式确实有效:

>>> db.torrents_sorted.find({'title._keywords': { '$all': [re.compile('river'), re.compile('the')]}}).count();
236
我不一定要寻找一个使用正则表达式的解决方案,但是需要在较短的字符串上匹配关键字,以便“riv”与“river”匹配,这似乎是正则表达式(或类似于sql)的理想选择


我的下一个想法是尝试传入一个javascript函数来执行列表上的正则表达式匹配,或者可能为每个正则表达式传入一个单独的函数(这似乎是在向我尖叫:),尽管我猜这会更慢,而且性能非常重要

您可能需要使用$and运算符。

好的,我有一个答案,这在另一个方面有点有趣。我在正则表达式中遇到的错误存在于mongodb的1.8版中,已经解决,如图所示

遗憾的是,负责db atm的托管公司无法提供2.0版,并且$and关键字被添加到了2.0版中,尽管感谢Samarth提供的调试帮助

因此,我编写了一个javascript函数来执行正则表达式匹配:

function () {
  var rs = [RegExp(".*river.*"), RegExp(".*runs.*")];

  for(var j = 0; j < rs.length; j++) {
    var val = false;
    for (var i = 0; !val && i < this.title._keywords.length; i++)
      val = rs[j].test(this.title._keywords[i]);

    if(!val) return false;
  }
  return true;
}
函数(){
var rs=[RegExp(.*river.*),RegExp(.*runs.*)];
对于(var j=0;j
这在O(n^2)时间内运行(不是很酷),但如果第一个正则表达式与关键字上的任何正则表达式都不匹配,则在线性时间内将失败(因为我正在寻找析取)


任何关于优化这一点的意见都将不胜感激,尽管如果这是我能为1.8找到的最佳解决方案,我可能必须在不久的将来找到其他地方来存储我的db,;)

db.torrents\u sorted.find({'title.{u keywords':{and::[“river”,“the”]}).count()
db.torrents\u sorted.find({'title':{{{and:::{{{u keywords:“river”},{'u keywords:“},{'the”}).count
all返回0个文档,即使没有正则表达式,同样的查询格式在没有正则表达式或使用正则表达式和pymongo的情况下也可以工作,这似乎表明这是一个bug,或者我遗漏了什么?在深入研究源代码之前,我想在这里验证我的理论,;)。事实上,他为我工作。让我查一下代码,看看我做了什么。您使用的$and运算符不正确。这是正确的版本。db.torrents_sorted.find({“$”和“:[{”title._关键字“:{$regex:'riv.*',$options:'i'}},{”title._关键字“:{$regex:'a',$options:'i'}]}).count();嗯,我一定是遗漏了什么,因为:
db.torrents\u sorted.find({“$and”:[{“title.”关键字:{$regex:'riv.*',$options:'I'},{“title.\u关键字:{$regex:'a',$options:'I'}}。)count()
db.torrents\u排序。find({“$and”:[{“title.\u关键字”:“river”},{“title.\u关键字”:“the”}]})。count()
返回0。您正在使用mongodb的开发版本吗?这个命令在MongoShell中有效吗?我在MongoShell中运行了这个命令。我使用的是在Linux上运行的Mongo DB 2.0.2版。它是最新的稳定版本,而不是开发版本。顺便说一句,你为什么在搜索中使用'the'。您的示例数据“\u关键字:[“a”、“河”、“流”、“穿过”]中至少没有它”
function () {
  var rs = [RegExp(".*river.*"), RegExp(".*runs.*")];

  for(var j = 0; j < rs.length; j++) {
    var val = false;
    for (var i = 0; !val && i < this.title._keywords.length; i++)
      val = rs[j].test(this.title._keywords[i]);

    if(!val) return false;
  }
  return true;
}