You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@lucene.apache.org by jp...@apache.org on 2025/04/07 21:21:48 UTC

(lucene) branch branch_10x updated: Use the same DocIdSetIterator impl for #all, #range and #empty. (#14451)

This is an automated email from the ASF dual-hosted git repository.

jpountz pushed a commit to branch branch_10x
in repository https://gitbox.apache.org/repos/asf/lucene.git


The following commit(s) were added to refs/heads/branch_10x by this push:
     new 64bcac56ada Use the same DocIdSetIterator impl for #all, #range and #empty. (#14451)
64bcac56ada is described below

commit 64bcac56ada0fb04e1fc4e549eae867b9d85ae54
Author: Adrien Grand <jp...@gmail.com>
AuthorDate: Mon Apr 7 23:08:51 2025 +0200

    Use the same DocIdSetIterator impl for #all, #range and #empty. (#14451)
    
    This helps reduce pollymorphism of call sites to `DocIdSetIterator` methods.
    
    Relates #14450
---
 .../org/apache/lucene/search/DocIdSetIterator.java | 160 +++++++--------------
 .../apache/lucene/search/TestDocIdSetIterator.java |  21 ++-
 2 files changed, 70 insertions(+), 111 deletions(-)

diff --git a/lucene/core/src/java/org/apache/lucene/search/DocIdSetIterator.java b/lucene/core/src/java/org/apache/lucene/search/DocIdSetIterator.java
index abfc985b688..a8e06e89afe 100644
--- a/lucene/core/src/java/org/apache/lucene/search/DocIdSetIterator.java
+++ b/lucene/core/src/java/org/apache/lucene/search/DocIdSetIterator.java
@@ -29,80 +29,15 @@ public abstract class DocIdSetIterator {
 
   /** An empty {@code DocIdSetIterator} instance */
   public static DocIdSetIterator empty() {
-    return new DocIdSetIterator() {
-      boolean exhausted = false;
-
-      @Override
-      public int advance(int target) {
-        assert !exhausted;
-        assert target >= 0;
-        exhausted = true;
-        return NO_MORE_DOCS;
-      }
-
-      @Override
-      public int docID() {
-        return exhausted ? NO_MORE_DOCS : -1;
-      }
-
-      @Override
-      public int nextDoc() {
-        assert !exhausted;
-        exhausted = true;
-        return NO_MORE_DOCS;
-      }
-
-      @Override
-      public long cost() {
-        return 0;
-      }
-    };
+    return new RangeDocIdSetIterator(0, 0);
   }
 
   /** A {@link DocIdSetIterator} that matches all documents up to {@code maxDoc - 1}. */
   public static DocIdSetIterator all(int maxDoc) {
-    return new DocIdSetIterator() {
-      int doc = -1;
-
-      @Override
-      public int docID() {
-        return doc;
-      }
-
-      @Override
-      public int nextDoc() {
-        return advance(doc + 1);
-      }
-
-      @Override
-      public int advance(int target) {
-        doc = target;
-        if (doc >= maxDoc) {
-          doc = NO_MORE_DOCS;
-        }
-        return doc;
-      }
-
-      @Override
-      public long cost() {
-        return maxDoc;
-      }
-
-      @Override
-      public void intoBitSet(int upTo, FixedBitSet bitSet, int offset) {
-        assert offset <= doc;
-        upTo = Math.min(upTo, maxDoc);
-        if (upTo > doc) {
-          bitSet.set(doc - offset, upTo - offset);
-          advance(upTo);
-        }
-      }
-
-      @Override
-      public int docIDRunEnd() throws IOException {
-        return maxDoc;
-      }
-    };
+    if (maxDoc < 0) {
+      throw new IllegalArgumentException("maxDoc must be >= 0, but got maxDoc=" + maxDoc);
+    }
+    return new RangeDocIdSetIterator(0, maxDoc);
   }
 
   /**
@@ -117,51 +52,62 @@ public abstract class DocIdSetIterator {
     if (minDoc < 0) {
       throw new IllegalArgumentException("minDoc must be >= 0 but got minDoc=" + minDoc);
     }
-    return new DocIdSetIterator() {
-      private int doc = -1;
+    return new RangeDocIdSetIterator(minDoc, maxDoc);
+  }
 
-      @Override
-      public int docID() {
-        return doc;
-      }
+  private static class RangeDocIdSetIterator extends DocIdSetIterator {
 
-      @Override
-      public int nextDoc() {
-        return advance(doc + 1);
-      }
+    private final int minDoc, maxDoc;
+    private int doc = -1;
 
-      @Override
-      public int advance(int target) {
-        if (target < minDoc) {
-          doc = minDoc;
-        } else if (target >= maxDoc) {
-          doc = NO_MORE_DOCS;
-        } else {
-          doc = target;
-        }
-        return doc;
-      }
+    RangeDocIdSetIterator(int minDoc, int maxDoc) {
+      // advance relies on minDoc <= maxDoc for correctness
+      assert minDoc <= maxDoc;
+      this.minDoc = minDoc;
+      this.maxDoc = maxDoc;
+    }
 
-      @Override
-      public long cost() {
-        return maxDoc - minDoc;
-      }
+    @Override
+    public int docID() {
+      return doc;
+    }
 
-      @Override
-      public void intoBitSet(int upTo, FixedBitSet bitSet, int offset) {
-        assert offset <= doc;
-        upTo = Math.min(upTo, maxDoc);
-        if (upTo > doc) {
-          bitSet.set(doc - offset, upTo - offset);
-          advance(upTo);
-        }
+    @Override
+    public int nextDoc() {
+      return advance(doc + 1);
+    }
+
+    @Override
+    public int advance(int target) {
+      if (target >= maxDoc) {
+        doc = NO_MORE_DOCS;
+      } else if (target < minDoc) {
+        doc = minDoc;
+      } else {
+        doc = target;
       }
+      return doc;
+    }
 
-      @Override
-      public int docIDRunEnd() throws IOException {
-        return maxDoc;
+    @Override
+    public long cost() {
+      return maxDoc - minDoc;
+    }
+
+    @Override
+    public void intoBitSet(int upTo, FixedBitSet bitSet, int offset) {
+      assert offset <= doc;
+      upTo = Math.min(upTo, maxDoc);
+      if (upTo > doc) {
+        bitSet.set(doc - offset, upTo - offset);
+        advance(upTo);
       }
-    };
+    }
+
+    @Override
+    public int docIDRunEnd() throws IOException {
+      return maxDoc;
+    }
   }
 
   /**
diff --git a/lucene/core/src/test/org/apache/lucene/search/TestDocIdSetIterator.java b/lucene/core/src/test/org/apache/lucene/search/TestDocIdSetIterator.java
index 2643c5ab366..7a4508f05a4 100644
--- a/lucene/core/src/test/org/apache/lucene/search/TestDocIdSetIterator.java
+++ b/lucene/core/src/test/org/apache/lucene/search/TestDocIdSetIterator.java
@@ -24,6 +24,19 @@ import org.apache.lucene.tests.util.LuceneTestCase;
 import org.apache.lucene.util.FixedBitSet;
 
 public class TestDocIdSetIterator extends LuceneTestCase {
+
+  public void testEmpty() throws IOException {
+    DocIdSetIterator disi = DocIdSetIterator.empty();
+    assertEquals(-1, disi.docID());
+    assertEquals(NO_MORE_DOCS, disi.nextDoc());
+    assertEquals(NO_MORE_DOCS, disi.docID());
+
+    disi = DocIdSetIterator.empty();
+    assertEquals(-1, disi.docID());
+    assertEquals(NO_MORE_DOCS, disi.advance(42));
+    assertEquals(NO_MORE_DOCS, disi.docID());
+  }
+
   public void testRangeBasic() throws Exception {
     DocIdSetIterator disi = DocIdSetIterator.range(5, 8);
     assertEquals(-1, disi.docID());
@@ -41,7 +54,7 @@ public class TestDocIdSetIterator extends LuceneTestCase {
         });
   }
 
-  public void testInvalidMin() throws Exception {
+  public void testInvalidRangeMin() throws Exception {
     expectThrows(
         IllegalArgumentException.class,
         () -> {
@@ -49,7 +62,7 @@ public class TestDocIdSetIterator extends LuceneTestCase {
         });
   }
 
-  public void testEmpty() throws Exception {
+  public void testEmptyRange() throws Exception {
     expectThrows(
         IllegalArgumentException.class,
         () -> {
@@ -57,7 +70,7 @@ public class TestDocIdSetIterator extends LuceneTestCase {
         });
   }
 
-  public void testAdvance() throws Exception {
+  public void testRangeAdvance() throws Exception {
     DocIdSetIterator disi = DocIdSetIterator.range(5, 20);
     assertEquals(-1, disi.docID());
     assertEquals(5, disi.nextDoc());
@@ -117,7 +130,7 @@ public class TestDocIdSetIterator extends LuceneTestCase {
     }
   }
 
-  public void testDocIDRunEnd() throws IOException {
+  public void testDocIDRunEndAll() throws IOException {
     DocIdSetIterator it = DocIdSetIterator.all(13);
     assertEquals(0, it.nextDoc());
     assertEquals(13, it.docIDRunEnd());