There is a bug in RangeQuery. In case of inclusive == false upperTerm
is chaged in rewrite according to a value from reader.terms(upperTerm).
This means that a RangeQuery has a state that is depending/changing with
search. Thus RangeQueries cannot be reused for several searches.
A JUnit test that demonstrates the problem and a patch that fixes it
are attatched.

Christoph

--
*****************************************************************
* Dr. Christoph Goller       Tel.:   +49 89 203 45734           *
* Detego Software GmbH       Mobile: +49 179 1128469            *
* Keuslinstr. 13             Fax.:   +49 721 151516176          *
* 80798 M�nchen, Germany     Email:  [EMAIL PROTECTED]  *
*****************************************************************
Index: RangeQuery.java
===================================================================
RCS file: 
/home/cvspublic/jakarta-lucene/src/java/org/apache/lucene/search/RangeQuery.java,v
retrieving revision 1.9
diff -u -r1.9 RangeQuery.java
--- RangeQuery.java     12 Aug 2003 09:17:53 -0000      1.9
+++ RangeQuery.java     5 Sep 2003 12:42:19 -0000
@@ -83,57 +83,57 @@
         {
             throw new IllegalArgumentException("Both terms must be for the same 
field");
         }
-        this.lowerTerm = lowerTerm;
+        
+        // if we have a lowerTerm, start there. otherwise, start at beginning
+        if (lowerTerm != null)
+            this.lowerTerm = lowerTerm;
+        else
+            this.lowerTerm = new Term(upperTerm.field(), "");
+
         this.upperTerm = upperTerm;
         this.inclusive = inclusive;
     }
 
     public Query rewrite(IndexReader reader) throws IOException {
-      BooleanQuery query = new BooleanQuery();
-      // if we have a lowerTerm, start there. otherwise, start at beginning
-      if (lowerTerm == null) lowerTerm = new Term(getField(), "");
-      TermEnum enumerator = reader.terms(lowerTerm);
-      try {
-        String lowerText = null;
-        String field;
-        boolean checkLower = false;
-          if (!inclusive) {             // make adjustments to set to exclusive
-            if (lowerTerm != null) {
-              lowerText = lowerTerm.text();
-              checkLower = true;
-            }
-            if (upperTerm != null) {
-              // set upperTerm to an actual term in the index
-              TermEnum uppEnum = reader.terms(upperTerm);
-              upperTerm = uppEnum.term();
-            }
-          }
-          String testField = getField();
-          do {
-            Term term = enumerator.term();
-            if (term != null && term.field() == testField) {
-              if (!checkLower || term.text().compareTo(lowerText) > 0) {
-                checkLower = false;
-                if (upperTerm != null) {
-                  int compare = upperTerm.compareTo(term);
-                  /* if beyond the upper term, or is exclusive and
-                   * this is equal to the upper term, break out */
-                  if ((compare < 0) || (!inclusive && compare == 0)) break;
+
+        BooleanQuery query = new BooleanQuery();
+        TermEnum enumerator = reader.terms(lowerTerm);
+
+        try {
+
+            boolean checkLower = false;
+            if (!inclusive) // make adjustments to set to exclusive
+                checkLower = true;
+
+            String testField = getField();
+
+            do {
+                Term term = enumerator.term();
+                if (term != null && term.field() == testField) {
+                    if (!checkLower || term.text().compareTo(lowerTerm.text()) > 0) {
+                        checkLower = false;
+                        if (upperTerm != null) {
+                            int compare = upperTerm.text().compareTo(term.text());
+                            /* if beyond the upper term, or is exclusive and
+                             * this is equal to the upper term, break out */
+                            if ((compare < 0) || (!inclusive && compare == 0))
+                                break;
+                        }
+                        TermQuery tq = new TermQuery(term); // found a match
+                        tq.setBoost(getBoost()); // set the boost
+                        query.add(tq, false, false); // add to query
+                    }
+                }
+                else {
+                    break;
                 }
-                TermQuery tq = new TermQuery(term); // found a match
-                tq.setBoost(getBoost());          // set the boost
-                query.add(tq, false, false); // add to query
-              }
-            }
-            else {
-              break;
             }
-          }
-          while (enumerator.next());
-      } finally {
-        enumerator.close();
-      }
-      return query;
+            while (enumerator.next());
+        }
+        finally {
+            enumerator.close();
+        }
+        return query;
     }
 
     public Query combine(Query[] queries) {
/*
 * Created on 05.09.2003
 *
 * To change the template for this generated file go to
 * Window>Preferences>Java>Code Generation>Code and Comments
 */
package org.apache.lucene.search;

import java.io.IOException;

import org.apache.lucene.analysis.WhitespaceAnalyzer;
import org.apache.lucene.document.Document;
import org.apache.lucene.document.Field;
import org.apache.lucene.index.IndexReader;
import org.apache.lucene.index.IndexWriter;
import org.apache.lucene.index.Term;
import org.apache.lucene.store.Directory;
import org.apache.lucene.store.RAMDirectory;

import junit.framework.TestCase;

/**
 * 
 * @author goller
 */
public class TestRangeQuery extends TestCase {

    
    public TestRangeQuery() {
        super();
    }

    int docCount = 0;
  
    void addDoc(IndexWriter writer, String content)
    {
        
      Document doc = new Document();
    
      doc.add(Field.Keyword("id","id" + docCount));
      doc.add(Field.UnStored("content", content));
    
      try {
        writer.addDocument(doc);
      }
      catch (IOException e) {
        e.printStackTrace();
      }
      docCount++;
      
    }
  
    public void testNotInclusive(){
        
        Directory dir = new RAMDirectory();
        IndexWriter writer = null;
        Searcher searcher = null;
        Query query = new RangeQuery(new Term("content", "A"), new Term("content", 
"C"), false);
        Hits hits = null;
        
        try {
          
          writer  = new IndexWriter(dir, new WhitespaceAnalyzer(), true);
          addDoc(writer, "A");
          addDoc(writer, "B");
          addDoc(writer, "C");
          addDoc(writer, "D");
          writer.close();
          
          searcher = new IndexSearcher(dir);
          hits = searcher.search(query);
          assertEquals(1, hits.length());
          searcher.close();
          
          writer  = new IndexWriter(dir, new WhitespaceAnalyzer(), true);
          addDoc(writer, "A");
          addDoc(writer, "B");
          addDoc(writer, "D");
          writer.close();
          
          searcher = new IndexSearcher(dir);
          hits = searcher.search(query);
          assertEquals(1, hits.length());
          searcher.close();
          
          writer  = new IndexWriter(dir, new WhitespaceAnalyzer(), false);
          addDoc(writer, "C");
          writer.close();
          
          searcher = new IndexSearcher(dir);
          hits = searcher.search(query);
          assertEquals(1, hits.length());
          searcher.close();
          
        }
        catch (IOException e) {
          e.printStackTrace();
        }
        
    }
    
    public void testInclusive(){
        
        Directory dir = new RAMDirectory();
        IndexWriter writer = null;
        Searcher searcher = null;
        Query query = new RangeQuery(new Term("content", "A"), new Term("content", 
"C"), true);
        Hits hits = null;
        
        try {
          
          writer  = new IndexWriter(dir, new WhitespaceAnalyzer(), true);
          addDoc(writer, "A");
          addDoc(writer, "B");
          addDoc(writer, "C");
          addDoc(writer, "D");
          writer.close();
          
          searcher = new IndexSearcher(dir);
          hits = searcher.search(query);
          assertEquals(3, hits.length());
          searcher.close();
          
          writer  = new IndexWriter(dir, new WhitespaceAnalyzer(), true);
          addDoc(writer, "A");
          addDoc(writer, "B");
          addDoc(writer, "D");
          writer.close();
          
          searcher = new IndexSearcher(dir);
          hits = searcher.search(query);
          assertEquals(2, hits.length());
          searcher.close();
          
          writer  = new IndexWriter(dir, new WhitespaceAnalyzer(), false);
          addDoc(writer, "C");
          writer.close();
          
          searcher = new IndexSearcher(dir);
          hits = searcher.search(query);
          assertEquals(3, hits.length());
          searcher.close();
          
        }
        catch (IOException e) {
          e.printStackTrace();
        }
        
    }


}

---------------------------------------------------------------------
To unsubscribe, e-mail: [EMAIL PROTECTED]
For additional commands, e-mail: [EMAIL PROTECTED]

Reply via email to