Using lucene 5.2.1, I have a BooleanQuery which ANDs together several term queries. The BooleanQuery and all the sub term queries are recreated with the 'new' operator each time I need to run the query. I would like to avoid calling 'new' and recreating so many query objects. Is it possible to update just the Terms in the term queries without re-creating the Boolean or term query objects each time?
1 Answers
No. Queries are cheap to construct, and are not designed for reuse.
It would be possible to reuse BooleanQuery, to some degree:
BooleanClause firstClause = boolQuery.clauses.get(0);
//change the first clause to use a different query.
firstClause.setQuery(myNewSubquery);
//Set the BooleanClause.Occur, if you wish
firstClause.setOccur(BooleanClause.Occur.MUST);
Of course, you could add new subqueries as usual, but there is no way to remove a subquery.
Reusing a TermQuery
is not possible. You can get the underlying Term
, but you can't modify it. Similar story for most queries. Some, you can figure out ways to modify if you look close enough, most you can't.
However, constructing queries should not be an expensive operation. I'm reasonably certain that, even if you could effectively reuse queries, it would have no discernible impact on performance. Running a query is the expensive part, not constructing it. And anyway, the first part of running a query is rewriting it, which involves creating a bunch of new queries anyway, so even if you could dodge constructing any yourself, Lucene is going to do it under the hood anyway.
If you have an actual performance issue you are trying to fix, I would recommend profiling to get more information about its actual cause. If you don't, then don't worry about it.