22 namespace Lucene.Net.Search
60 private void InitBlock()
62 bucketTable =
new BucketTable();
65 private sealed
class BooleanScorerCollector:
Collector
67 private BucketTable bucketTable;
71 public BooleanScorerCollector(
int mask, BucketTable bucketTable)
74 this.bucketTable = bucketTable;
76 public override void Collect(
int doc)
78 BucketTable table = bucketTable;
79 int i = doc & Lucene.Net.Search.BooleanScorer.BucketTable.MASK;
80 Bucket bucket = table.buckets[i];
82 table.buckets[i] = bucket =
new Bucket();
84 if (bucket.doc != doc)
88 bucket.score = scorer.Score();
92 bucket.next = table.first;
98 bucket.score += scorer.Score();
104 public override void SetNextReader(
IndexReader reader,
int docBase)
109 public override void SetScorer(
Scorer scorer)
111 this.scorer = scorer;
114 public override bool AcceptsDocsOutOfOrder
124 private sealed
class BucketScorer:
Scorer
127 internal float score;
128 internal int doc = NO_MORE_DOCS;
130 public BucketScorer():base(null)
134 public override int Advance(
int target)
139 public override int DocID()
144 public override int NextDoc()
149 public override float Score()
155 internal sealed
class Bucket
157 internal int doc = - 1;
158 internal float score;
161 internal Bucket next;
165 internal sealed
class BucketTable
167 private void InitBlock()
169 buckets =
new Bucket[SIZE];
171 public const int SIZE = 1 << 11;
172 public static readonly
int MASK;
174 internal Bucket[] buckets;
175 internal Bucket first = null;
184 return new BooleanScorerCollector(mask,
this);
197 internal sealed
class SubScorer
200 public bool required =
false;
201 public bool prohibited =
false;
203 public SubScorer next;
205 public SubScorer(
Scorer scorer,
bool required,
bool prohibited,
Collector collector, SubScorer next)
207 this.scorer = scorer;
208 this.required = required;
209 this.prohibited = prohibited;
210 this.collector = collector;
215 private SubScorer scorers = null;
216 private BucketTable bucketTable;
217 private int maxCoord = 1;
218 private float[] coordFactors;
219 private int requiredMask = 0;
220 private int prohibitedMask = 0;
221 private int nextMask = 1;
222 private int minNrShouldMatch;
224 private Bucket current;
225 private int doc = - 1;
228 System.Collections.Generic.List<
Scorer> optionalScorers, System.Collections.Generic.List<
Scorer> prohibitedScorers)
232 this.minNrShouldMatch = minNrShouldMatch;
234 if (optionalScorers != null && optionalScorers.Count > 0)
236 foreach (
Scorer scorer
in optionalScorers)
239 if (scorer.
NextDoc() != NO_MORE_DOCS)
241 scorers =
new SubScorer(scorer,
false,
false, bucketTable.NewCollector(0), scorers);
246 if (prohibitedScorers != null && prohibitedScorers.Count > 0)
248 foreach(
Scorer scorer
in prohibitedScorers)
251 nextMask = nextMask << 1;
252 prohibitedMask |= mask;
253 if (scorer.
NextDoc() != NO_MORE_DOCS)
255 scorers =
new SubScorer(scorer,
false,
true, bucketTable.NewCollector(mask), scorers);
260 coordFactors =
new float[maxCoord];
262 for (
int i = 0; i < maxCoord; i++)
264 coordFactors[i] = sim.
Coord(i, maxCoord - 1);
269 public override bool Score(
Collector collector,
int max,
int firstDocID)
273 BucketScorer bs =
new BucketScorer();
278 bucketTable.first = null;
280 while (current != null)
285 if ((current.bits & prohibitedMask) == 0 && (current.bits & requiredMask) == requiredMask)
288 if (current.doc >= max)
291 current = current.next;
292 tmp.next = bucketTable.first;
293 bucketTable.first = tmp;
297 if (current.coord >= minNrShouldMatch)
299 bs.score = current.score * coordFactors[current.coord];
300 bs.doc = current.doc;
301 collector.
Collect(current.doc);
305 current = current.next;
308 if (bucketTable.first != null)
310 current = bucketTable.first;
311 bucketTable.first = current.next;
317 end += BucketTable.SIZE;
318 for (SubScorer sub = scorers; sub != null; sub = sub.next)
320 int subScorerDocID = sub.scorer.DocID();
321 if (subScorerDocID != NO_MORE_DOCS)
323 more |= sub.scorer.Score(sub.collector, end, subScorerDocID);
326 current = bucketTable.first;
328 while (current != null || more);
333 public override int Advance(
int target)
335 throw new System.NotSupportedException();
338 public override int DocID()
343 public override int NextDoc()
348 while (bucketTable.first != null)
351 current = bucketTable.first;
352 bucketTable.first = current.next;
355 if ((current.bits & prohibitedMask) == 0 && (current.bits & requiredMask) == requiredMask && current.coord >= minNrShouldMatch)
357 return doc = current.doc;
363 end += BucketTable.SIZE;
364 for (SubScorer sub = scorers; sub != null; sub = sub.next)
366 Scorer scorer = sub.scorer;
367 sub.collector.SetScorer(scorer);
368 int doc = scorer.
DocID();
371 sub.collector.Collect(doc);
374 more |= (doc != NO_MORE_DOCS);
377 while (bucketTable.first != null || more);
379 return this.doc = NO_MORE_DOCS;
382 public override float Score()
384 return current.score * coordFactors[current.coord];
389 Score(collector, System.Int32.MaxValue, NextDoc());
392 public override System.String ToString()
394 System.Text.StringBuilder buffer =
new System.Text.StringBuilder();
395 buffer.Append(
"boolean(");
396 for (SubScorer sub = scorers; sub != null; sub = sub.next)
398 buffer.Append(sub.scorer.ToString());
402 return buffer.ToString();