@@ -231,16 +231,25 @@ protected static class DefaultBulkScorer extends BulkScorer {
231231 private final Scorer scorer ;
232232 private final DocIdSetIterator iterator ;
233233 private final TwoPhaseIterator twoPhase ;
234+ private final ScoreMode scoreMode ;
235+ private DocAndScoreBuffer buffer ;
236+ private SimpleScorable scorable ;
234237
235238 /** Sole constructor. */
236239 public DefaultBulkScorer (Scorer scorer ) {
240+ this (scorer , null );
241+ }
242+
243+ /** Sole constructor. */
244+ public DefaultBulkScorer (Scorer scorer , ScoreMode scoreMode ) {
237245 this .scorer = Objects .requireNonNull (scorer );
238246 this .twoPhase = scorer .twoPhaseIterator ();
239247 if (twoPhase == null ) {
240248 this .iterator = scorer .iterator ();
241249 } else {
242250 this .iterator = twoPhase .approximation ();
243251 }
252+ this .scoreMode = scoreMode ;
244253 }
245254
246255 @ Override
@@ -251,9 +260,14 @@ public long cost() {
251260 @ Override
252261 public int score (LeafCollector collector , Bits acceptDocs , int min , int max )
253262 throws IOException {
254- collector .setScorer (scorer );
255263 DocIdSetIterator competitiveIterator = collector .competitiveIterator ();
256264
265+ if (scoreMode != null && scoreMode .needsScores () && competitiveIterator == null ) {
266+ return batchScore (collector , acceptDocs , min , max );
267+ }
268+
269+ collector .setScorer (scorer );
270+
257271 if (competitiveIterator != null ) {
258272 if (competitiveIterator .docID () > min ) {
259273 min = competitiveIterator .docID ();
@@ -290,6 +304,37 @@ public int score(LeafCollector collector, Bits acceptDocs, int min, int max)
290304 return iterator .docID ();
291305 }
292306
307+ private int batchScore (LeafCollector collector , Bits acceptDocs , int min , int max )
308+ throws IOException {
309+ if (buffer == null ) {
310+ buffer = new DocAndScoreBuffer ();
311+ }
312+ if (scorable == null ) {
313+ scorable = new SimpleScorable ();
314+ }
315+
316+ collector .setScorer (scorable );
317+ scorer .setMinCompetitiveScore (scorable .minCompetitiveScore );
318+
319+ if (scorer .docID () < min ) {
320+ scorer .iterator ().advance (min );
321+ }
322+
323+ for (scorer .nextDocsAndScores (max , acceptDocs , buffer );
324+ buffer .size > 0 ;
325+ scorer .nextDocsAndScores (max , acceptDocs , buffer )) {
326+ for (int i = 0 , size = buffer .size ; i < size ; i ++) {
327+ float score = scorable .score = buffer .scores [i ];
328+ if (score >= scorable .minCompetitiveScore ) {
329+ collector .collect (buffer .docs [i ]);
330+ }
331+ }
332+ scorer .setMinCompetitiveScore (scorable .minCompetitiveScore );
333+ }
334+
335+ return scorer .docID ();
336+ }
337+
293338 private static void scoreIterator (
294339 LeafCollector collector , Bits acceptDocs , DocIdSetIterator iterator , int max )
295340 throws IOException {
0 commit comments