Cloudant - Lucene使用存储为文本的数字搜索范围

时间:2015-12-14 14:09:29

标签: lucene cloudant

我在Cloudant中有许多文档,其ID字段的类型为字符串。 ID可以是一个简单的字符串,例如" aaa"," bbb"或者作为文本存储的号码,例如" 111"," 222"等我需要能够使用上述字段进行全文搜索,但我遇到了一些问题。

假设我有两个文件,ID =" aaa"和ID =" 111",然后用查询搜索:

  • ID:AAA
  • ID:" AAA"
  • ID:[aaa to zzz]
  • ID:[" AAA" TO" zzz"]

按预期返回第一个文档

  • ID:111

什么都不返回,但是

  • ID:" 111"

返回第二个文档,因此至少有一种方法可以检索它。

不幸的是,在搜索范围时:

  • ID:[111至999]
  • ID:[" 111" TO" 999"]

我没有得到任何结果,我不知道如何解决这个问题。这种情况有什么特殊的语法吗?

更新:

索引功能:

function(doc){
  if(!doc.ID) return;
  index("ID", doc.ID, { index:'not_analyzed_no_norms', store:true });
}

将索引更改为已分析并没有帮助。分析器本身是关键字,但更改为标准也无济于事。

更新2

只是添加更多上下文,因为我认为我错过了一个关键点。将使用范围搜索字段I索引,并且用户可以提供最小值和最大值。因此,有可能其中一个将数字存储为字符串,而其他将是标准的非数字文本。例如,搜索所有ID> =" 11"和ID< =" foo"。

Assumig该数据库包含ID为#" 1"," 5"," alpha"," beta"," gamma",此查询应返回" 5"," alpha"," beta"。请注意" 5"实际上应该被退回,因为字符串" 5"大于字符串" 11"。

3 个答案:

答案 0 :(得分:2)

首先,我建议使用关键字分析器,这样您就可以在索引和搜索过程中控制正确的标记化。

$tableData3 = array_diff($tableData, $arr);

要使用_id" 111"检索您的文档,请使用以下范围查询:

"analyzer": "keyword",
"index": "function(doc){\n  if(!doc.ID) return;\n  index(\"ID\", doc.ID, {store:true });\n}

如果您使用查询curl -X GET "http://.../facetrangetest/_design/ddoc/_search/f?q=ID:\[111%20TO%A\]" ,Cloudant搜索会查看范围大小的数字,将其解释为NumericRangeQuery;因为您的ID为" 111"是一个String,它不会是返回结果的一部分。在查询[111%20TO%20A]中包含一个字符串,将使Cloudant将其解释为对字符串的范围查询。

答案 1 :(得分:1)

您可以像这样返回两个文档:

q=ID:["111" TO "CCC"]

这是一个有效的实例:

https://rajsingh.cloudant.com/facetrangetest/_design/ddoc/_search/f?q=ID:[%22111%22%20TO%20%22CCC%22]

我发现了一些奇怪的东西。看起来字符串上的范围查询仅在至少一个范围值是字符串时才起作用。查询ID:["111" TO "555"]也没有返回任何内容,所以这可能会以某种方式解析为数字查询?可能是一个错误。

答案 2 :(得分:1)

这也可以使用查询中的正则表达式来实现。有点像这样:

curl -X POST "https://.../facetrangetest/_design/ddoc/_search/f" -d '{"q":"ID:/<23-758>/"}' | jq .

这个正则表达式意味着检索ID字段为23到758的所有文档。斜杠:/ /用于包含正则表达式;区间包含在<>内。