我已经在lucene中构建了一个查询以替换SQL查询,但得出的结论是lucene查询的速度是多个数量级的。我的意思是慢,从250ms到5000ms,这是不可接受的。设置有点特殊,我想问题出在哪里。
被索引和搜索的主要字段属于Map<String, String>
,并映射为:
@ElementCollection(targetClass = String.class)
@CollectionTable(name = "data")
private Map<String, String> data;
或者换句话说,该实体具有带键值对的关联表。我们想要搜索这些值,但仅限于特定键。因此,如果我们遇到满足我们需求的密钥,我的现场桥实施将在文档中输入。 (我们显然不想在索引中存储每个键。)
主要查询实际上并不特别:
FullTextSession fullTextSession = Search.getFullTextSession(getCurrentSession());
try {
fullTextSession.createIndexer(Form.class).startAndWait();
} catch (InterruptedException ex) {
LOG.error("Exception when indexing: ", ex);
}
QueryBuilder builder = fullTextSession.getSearchFactory().buildQueryBuilder().forEntity(Entity.class).get();
org.apache.lucene.search.Query query;
BooleanJunction booleanJunction = builder.bool();
booleanJunction.must(builder.keyword().onFields("data")
.matching(searchString).createQuery());
我的问题是,我在做错了这个查询需要这么长时间来处理?如果您希望我提供任何可能有助于您解决此问题的额外信息,请询问并提供。我不知道包含TwoWayFieldBridge
代码有多相关,但如果问题可能在那里,请问。
更新 从这个意义上说,接受的答案是正确的,这导致了显着的放缓。我建议你的应用程序从一开始就被编入索引,如果这是不可能的,你可以附加一种startuplistener(取决于所使用的框架或上下文),并使用此代码启动索引器。请注意,您需要打开足够的可用连接,否则可能会阻止您的应用程序启动。
答案 0 :(得分:1)
如果您显示“搜索代码”的代码,那么您的问题是,您在每次搜索时索引数据。这为Form
类索引:
try {
fullTextSession.createIndexer(Form.class).startAndWait();
} catch (InterruptedException ex) {
LOG.error("Exception when indexing: ", ex);
}
您只希望执行一次此操作,或者在数据更改时执行此操作。您的代码使用质量索引器API来索引现有数据(createIndexer(Form.class).startAndWait()
)。此方法的目的是创建现有数据的初始索引。一旦数据被索引,您可以例如依赖于Hibernate Search的自动索引,该索引将为数据更改注册监听器,并且仅索引添加或更改的索引数据。或者,如果您需要/需要此级别的控制,您可以手动索引。我建议您参考文档以了解有关这些不同类型的索引的更多信息。