首页 > 解决方案 > Hibernate Search + Lucene:后备搜索停用词

问题描述

我在 5.11.5 版本中使用 Hibernate Search 和 Apache Lucene 5.5.5。在我的示例中,我使用了StopFilterFactory在中定义的默认停用词集StopAnalyzer.ENGLISH_STOP_WORDS_SET(例如“this”、“will”、“be”、...)。

现在我索引了三首音乐歌曲标题:“我会生存”、“我们会摇滚你”、“这将是”

我的搜索查询是“摇滚会让我活下来”。所以我发现“我会活下来”和“我们会摇滚你”,而不是“这将是”,因为这首歌完全由停用词组成。如果我搜索“这将是”,那么我什么也找不到。

现在我需要对这些歌曲进行“后备”搜索:当且仅当歌曲标题完全由停用词组成时,如果所有单词都包含在我的搜索字符串中,我想找到它们。所以搜索“我将成为一名消防员”不会找到“这将是”,但搜索“我这样”会找到“这将是”。

你知道我怎么能做到这一点吗?

标签: lucenehibernate-search

解决方案


就个人而言,在这种情况下,我会考虑简单地取消StopFilterFactory.

停用词的主要问题是它们在许多文档中出现得非常频繁,因此考虑到它们没有太大意义,它们以一种完全不成比例的方式影响相关性(分数)。

所以我们通常根本不索引它们来解决这个问题。作为奖励,这可能会在一定程度上减少索引大小。

但还有另一种解决方案,即保留停用词并修复分数的计算方式。在 Lucene 中,负责计算分数的组件称为Similarity. Hibernate Search 5 / Lucene 5.5 中的默认值是ClassicSimilarity,它会遇到停用词的问题。另一个较新的实现是 BM25,该实现在停用词方面具有更好的行为:它不会让它们对分数产生太大影响。如果您有兴趣,可以在这里找到深入的解释。请注意,BM25ClassicSimilarity在较新版本的 Lucene 和 Hibernate Search 以及 Elasticsearch 中被替换为默认相似度。

我建议您更改 Similarity to use org.apache.lucene.search.similarities.BM25Similarity,删除您的停用词过滤器,然后重新索引您的数据,然后再次测试您的查询。您是否在顶部附近获得相关点击?索引大小仍然可以管理吗?您的查询“这将是”是否匹配?如果是这样,切换到 BM25 是一个完全可行的解决方案。

请注意,您还可以考虑升级到默认使用 BM25 的Hibernate Search 6 。


推荐阅读