在查询短语中添加单词应该在Lucene中过滤结果

时间:2012-02-29 12:23:29

标签: java lucene

即使已经回答并接受

,我也会在可能的情况下向这个问题提供+100的奖励

我正在使用Lucene 3.2,这是我在索引和代码中的内容:

  • 每个索引文档超过10个字段。
  • 查询短语中的
  • OR操作数(即:“我的lucene搜索”变为“我的或者lucene OR搜索”)。
  • MultiFieldQueryParser在所有字段中都有Occur.SHOULD
  • 包含所有其他字段的特定默认字段(如此解决方案How to do a Multi field - Phrase search in Lucene?中所建议的那样)。

我想要达到什么目的?一种类似Google的搜索,让我解释一下:

  • 在所有领域搜索
  • 评分结果(特定字段的提升等)
  • 在查询词组中添加字词过滤结果

我已达到各个方面,但最后一个方面。我的问题如下:

  • 如果我只在包含所有其他字段的默认字段中搜索,我的评分不会很高
  • 仅使用AND操作数进行搜索我得到过滤结果,只获得在一个字段中包含整个查询短语的结果。
  • 仅使用OR操作数进行搜索,只需在查询中使用一个单词,,在向查询词组添加更多单词时,结果会显着增加而不是过滤(就像谷歌一样。)
  • 我不知道如何从另一个
  • 过滤一个查询

这是我对查询解析器的实际调用:

MultiFieldQueryParser.parse(
    Version.LUCENE_31,
    OrQueryWords, //query words separated with OR operand
    searchFields, //String[] searchFields; // all fields
    occurs, //Occur[] occurs; {Occur.SHOULD, Occur.SHOULD, etc..}
    getFullTextSession().getSearchFactory().getAnalyzer(Product.class)
);

此查询的toString()打印如下内容:

(field1:"word1 word2" (field1:word1 field1:word2)) (field2:"word1 word2" (...)) etc.

现在我正在尝试添加默认字段(包含所有其他字段的字段),其中查询字以AND操作数和Occur.MUST分隔:

MultiFieldQueryParser.parse(
    Version.LUCENE_31,
    AndQueryWords, //query words separated with AND operand
    new String[] {"defaultField"},
    new Occur[] {Occur.MUST},
    getFullTextSession().getSearchFactory().getAnalyzer(Product.class)
);

此查询的toString()打印出:

+(default:"word1 word2" (+default:word1 +default:word2))

我如何与两个查询相交?有没有其他解决方案可以达到它?

2 个答案:

答案 0 :(得分:1)

我用来解决类似问题的方法是基于分数限制结果数量。

不幸的是,Lucene没有提供开箱即用的功能,他们也不鼓励这种方法(http://wiki.apache.org/lucene-java/ScoresAsPercentages)。主要关注点是得分的绝对值毫无意义。

我使用得分的相对值进行过滤:我选择了最高得分,然后从中计算出最低接受得分(假设为maxScore / 5)并仅留下满足此标准的结果。

答案 1 :(得分:1)

我不确定你想要达到什么目标,因此我将在处理多字段多项查询时给你一些关于如何自定义评分的提示。

两个查询的交叉点

您似乎对默认字段结果集上的联合查询以及所有字段评分的析取查询感到满意。通过将后者用作主要查询,将前者用作过滤器,您可以充分利用这两个世界。

例如:

Query mainQuery, filterQuery;

BooleanQuery query = new BooleanQuery();

// add the main query for scoring
query.add(mainQuery, Occur.SHOULD);

// prevent the filter query to participate in the scoring
filter.setBoost(0);
// make the filter query required
query.add(filterQuery, Occur.MUST);

最低匹配条款

如果对所有子句进行AND限制过于严格,并且所有子句的OR限制不够严格,那么您可以通过设置minimum number of SHOULD clauses that must match来执行某些操作,以便在结果集中显示文档。

然后困难的部分是找到合适的公式来计算必须匹配的最小SHOULD子句数,以便获得最佳用户体验。

例如,假设您希望3/4个SHOULD子句的ceil匹配。从两个子句开始查询并添加最多5个子句的子句将产生以下结果数量的演变。

  • 2个条款=> ceil(2 * 3/4)= 2:所有条款必须匹配
  • 3个条款=> ceil(3 * 3/4)= 3:3/4条款必须匹配(新条款是必需的,较少结果)
  • 4个条款=> ceil(4 * 3/4)= 3:3/4条款必须匹配(其中一个条款是可选的,更多结果)
  • 5个条款=> ceil(5 * 3/4)= 4:4/5条款必须匹配(可能更多,可能更少的结果,取决于新术语与4个第一个术语的共现)

无论如何,使用此功能,随着子句数量的增加,结果数量缩小的唯一方法是进行纯粹的连接查询。