RethinkDB:​​获取包含任何字段中的字符串的所有文档

时间:2014-01-05 14:07:36

标签: rethinkdb rethinkdb-python

我想执行一个查询,它将在其任何字段中返回包含给定字符串的所有文档。例如,假设我有一个“用户”表,我正在查找包含“john”的所有文档,返回的结果可以是:

[{"first_name": "jhon", "last_name": "watson"}, {"first_name": "elton", "last_name": "john"}, {"first_name": "sherlock", "last_name": "holmes", "best_friend": "john watson"}]

我如何在rethinkdb中执行此操作? javascript答案会做,python实现会更好。

3 个答案:

答案 0 :(得分:2)

不幸的是,由于ReQL没有像{python这样的values函数,因此查询更加困难。但它确实有一个keys函数,所以让我们使用它来制作values函数,如下所示:

def values(doc):
    return doc.keys().map(lambda x: doc[x])

现在我们已经找到了一个包含其中一个键中的字符串的文档非常简单:

def has_str(doc, str):
    return values(doc).map(match(str)).reduce(lambda x,y: x | y)

最后我们可以把它们放在一起:

r.table("users").filter(lambda doc: has_str(doc, str))

理论上你可以在一个大查询中完成这一切,但我真的很喜欢分解中等复杂的查询。这种方法非常好用的是,如果它不起作用,每个函数都有一组非常简单的语义,所以你可以单独调试它们。

答案 1 :(得分:2)

看起来您可以将整个文档强制转换为字符串,然后搜索:

r.db('database').table('table).filter(function(doc) {
  return doc.coerceTo('string').match('querystring');
});

这个解决方案并不像其他提供的那样灵巧,但对我来说运行速度要快得多,并且到目前为止提供了相同的结果。

答案 2 :(得分:0)

对于那些发现自己试图在javascript中解决这个问题的人来说,这大致可以转换为:

function values(doc) {
  return doc.keys().map(function(key) {
    return doc(key);
  });
}

function contains(doc, string) {
  return values(doc).map(function(val) {
    return r.branch(val.match(string), true, false);
  }).reduce(function(left, right) {
    return left.or(right);
  });
}

var query = r.db('database').table('table').filter(function(doc) {
  return contains(doc, "some string");
});

query.run().then(function(results) {
  console.log(results);
});

欢迎改进!