当前位置: 首页 > 知识库问答 >
问题:

Hibernate Search/Lucene--用单个查询搜索无关实体并对其进行排名

拓拔烨赫
2023-03-14

我使用hibernate search和lucene进行全文搜索,因为我可以成功地跨特定字段搜索给定的模型实体。

然而,不是一次搜索一种类型的实体,我想实现一种“通用”搜索,在这种搜索中,同时搜索不同的实体类型,将搜索短语与每个不同实体类型上的适当字段匹配,然后根据与搜索词的相关性对结果进行排序,而不考虑实体类型。

例如,假设我有不同的实体,Foo和Bar

@Entity
@Indexed
@AnalyzerDef(
  name="fulltext",
  tokenizer=@TokenizerDef(factory=StandardTokenizerFactory.class),
  filters={
    @TokenFilterDef(factory=LowerCaseFilterFactory.class),
    @TokenFilterDef(factory=SnowballPorterFilterFactory.class, 
      params={@Parameter(name="language", value="English") })
  }
)
public class Foo {

  @Id
  @GeneratedValue(strategy = GenerationType.AUTO)
  private Integer fooId;

  @Column
  @Field 
  @Analyzer(definition="fulltext") 
  private String fieldA;

  ...
@Entity
@Indexed
public class Bar {

  @Id
  @GeneratedValue(strategy = GenerationType.AUTO)
  private Integer barId;

  @Column
  @Field 
  @Analyzer(definition="fulltext") 
  private String fieldB;

  @Column
  @Field 
  @Analyzer(definition="fulltext") 
  private String fieldC;

  ...
fullTextSession = Search.getFullTextSession(hibernateSession);
Query query = fullTextSession.createFullTextQuery(
                fullTextSession
                  .getSearchFactory()
                  .buildQueryBuilder()
                  .forEntity(Foo.class)
                  .get()
                  .keyword()
                  .onFields("fieldA")
                  .matching("some text")
                  .createQuery(),
              Foo.class);
 query.list() // gets ranked list of Foo entities matching "some text"

显然,上面的Lucene查询是特定于Foo实体的,甚至是Foo.fielda

那么,是否可以修改Lucene查询,使其也包括Bar结果,在Bar.fieldb和Bar.fieldc字段上进行匹配?

我知道fulltextSession.createFullTextQuery(fulltextSession,Class...)方法也将接受Bar.class以返回Bar结果,但我不知道如何修改实际查询以首先搜索Bar实体。

fullTextQuery.score:返回查询中的文档分数。分数可以方便地比较给定查询的一个结果和另一个结果,但在比较不同查询的结果时就没用了。

很抱歉,如果我在这里覆盖了一些老生常谈的地方,但我已经搜索了几个小时,显然是在错误的地方,但在文档中找不到任何有用的东西,这很令人沮丧,因为我认为这是Lucene的一个相当常见的用例。

共有1个答案

充鑫鹏
2023-03-14

您可以编写两个查询,并通过booleanquery使用occur.show将它们组合在一起。然后使用CreateFullTextQuery(booleanQuery,foo.class,bar.class);搜索这两种类型的实体。

 类似资料:
  • 我的任务是使用lucene在我们的产品表中搜索。我已经创建了一个索引,正在使用带有多个字段的QueryParser进行搜索,但结果不是我所需要的。我有一个存储为LM10的产品,但如果搜索词是LM 10,我希望能够找到它,但如果搜索词是Fred LM10或Fred LM 10,它也必须能够匹配。你知道我如何在Lucene做到这一点吗。 提前谢谢

  • 问题内容: 我有一个包含多个字段的索引,其中一个是字符串字段,我在其中存储产品的类别名称…例如“电子”,“家庭”,“花园”等 我正在执行布尔查询以按名称,价格和类别查找产品,但是我不确定如何执行“或”搜索,以便可以同时查询两个类别。 我当前的查询如下所示: 这对于一个类别的搜索来说效果很好,但是我不确定如何搜索将是两个类别的“ Electronics OR Home”。 问题答案: 您可以这样写:

  • 我正在使用Sitecore搜索数据库中的项目。

  • 我使用这个分析器创建了一个模型: 我实现了如下所示的查询。我得到了所有预期的结果,除了像“A.B.C”这样的结果。我做错了什么?我哪里误解了事情? 我的代码基于以下资源:

  • 我想索引和搜索使用Lucene索引的数据片段。 例如。物品及其颜色 搜索示例 可能的解决办法 根据我在答案中发现的,显然我可以使用这种格式将这些添加到一个字段中。 如果我现在用这种格式的数据进行搜索,我不会得到任何结果。 null

  • Hibernate5.2.10 查询DSL(jpa,apt)4.1.4 Spring Boot 1.5.6 Spring Data JPA(因此,使用存储库) 存储库扩展 选择以下meetupCampaign.id=x *meetupCampaign.ApprovalStatus=y的关联会议: *meetupCampaign.id=x *meetupCampaign.ApprovalStatus