jackrabbit-dev mailing list archives

Site index · List index
Message view « Date » · « Thread »
Top « Date » · « Thread »
From Marcel Reutegger <marcel.reuteg...@gmx.net>
Subject Re: DescendantSelfAxisWeight ChildAxisQuery performance
Date Fri, 30 Nov 2007 10:54:45 GMT
Ard Schrijvers wrote:
>> Ard Schrijvers wrote:
>>> Query q = qm.createQuery("stuff//*[@count]", Query.XPATH); if (q 
>>> instanceof QueryImpl) {
>>>     // limit the result set
>>>     ((QueryImpl) q).setLimit(1);
>>> }
>>> Since my "stuff//*[@count]" gives me 1.200.000, it makes 
>> perfect sense 
>>> to users I think, that even with our patches and a working 
>> cache, that 
>>> retaining them all would be slow. But if I set the limit to 
>> 1 or 10, I 
>>> would expect to have performance (certainly when you have not 
>>> implemented any AccessManager).
>>> But, if I set limit to 1, why would we have to check all 1.200.000 
>>> parents wether the path is correct?
>> I'm not quite sure if this is a valid/common use case. I 
>> can't imagine doing a query like this without using an "order 
>> by" clause. Because without an "order by" you will just get a 
>> random node. But if you use an "order by" you need to get all 
>> nodes first anyway.

see my comments below.

> This is not my point. Wether you have an order by or not, lucene will
> compute the score of all hits anyway. So, no order by, does not mean
> that lucene does not order: it orders on score (but ofcourse you already
> know that :-) )
> So, my thing holds with and without order by. 

WRT lucene this is correct. but the same is not true for JCR. if there is no 
order by the implementation is free to return the nodes in any order.

I did a quick test and wrote a custom IndexSearcher (see below), which collects 
only the first n matching documents. the test query then executed much faster 
because the number of DescendantSelfAxisScorer.isValid() calls dropped drastically.

There is one drawback though. you don't know the total number of results. in 
this case it might be OK to return -1 for the RangeIterator.getSize().

the order by is more difficult to solve. what we could try is order the result 
of the sub query first and then run the descendant axis test against the context 
nodes. DescendantSelfAxisQuery does not add nodes to the sub query but only 
limits the set subsequent ordering can be skipped. this requires that we need to 
pass along ordering information with the scorer. e.g. index-order, relevance, 

In any case we should create a jira issue for it.


public class JackrabbitIndexSearcher extends IndexSearcher {

     private final IndexReader reader;

     public JackrabbitIndexSearcher(IndexReader r) {
         this.reader = r;

     // inherit javadoc
     public TopDocs search(Weight weight, Filter filter, int nDocs)
             throws IOException {
         TopDocCollector collector = new TopDocCollector(nDocs);
         Scorer scorer = weight.scorer(reader);
         if (scorer != null) {
             while (scorer.next() && nDocs-- > 0) {
               collector.collect(scorer.doc(), scorer.score());
         return collector.topDocs();

View raw message