use of org.apache.lucene.search.TwoPhaseIterator in project lucene-solr by apache.
the class Filter method createWeight.
//
// Query compatibility
//
@Override
public Weight createWeight(IndexSearcher searcher, boolean needsScores, float boost) throws IOException {
return new Weight(this) {
@Override
public void extractTerms(Set<Term> terms) {
}
@Override
public Explanation explain(LeafReaderContext context, int doc) throws IOException {
final Scorer scorer = scorer(context);
final boolean match = (scorer != null && scorer.iterator().advance(doc) == doc);
if (match) {
assert scorer.score() == 0f;
return Explanation.match(0f, "Match on id " + doc);
} else {
return Explanation.match(0f, "No match on id " + doc);
}
}
@Override
public Scorer scorer(LeafReaderContext context) throws IOException {
final DocIdSet set = getDocIdSet(context, null);
if (set == null) {
return null;
}
if (applyLazily && set.bits() != null) {
final Bits bits = set.bits();
final DocIdSetIterator approximation = DocIdSetIterator.all(context.reader().maxDoc());
final TwoPhaseIterator twoPhase = new TwoPhaseIterator(approximation) {
@Override
public boolean matches() throws IOException {
return bits.get(approximation.docID());
}
@Override
public float matchCost() {
// TODO use cost of bits.get()
return 10;
}
};
return new ConstantScoreScorer(this, 0f, twoPhase);
}
final DocIdSetIterator iterator = set.iterator();
if (iterator == null) {
return null;
}
return new ConstantScoreScorer(this, 0f, iterator);
}
};
}
use of org.apache.lucene.search.TwoPhaseIterator in project crate by crate.
the class GenericFunctionQuery method createWeight.
@Override
public Weight createWeight(IndexSearcher searcher, ScoreMode scoreMode, float boost) throws IOException {
return new Weight(this) {
@Override
public boolean isCacheable(LeafReaderContext ctx) {
if (SymbolVisitors.any(s -> s instanceof Function && !((Function) s).isDeterministic(), function)) {
return false;
}
var fields = new ArrayList<String>();
RefVisitor.visitRefs(function, ref -> fields.add(ref.column().fqn()));
return DocValues.isCacheable(ctx, fields.toArray(new String[0]));
}
@Override
public void extractTerms(Set<Term> terms) {
}
@Override
public Explanation explain(LeafReaderContext context, int doc) throws IOException {
final Scorer s = scorer(context);
final boolean match;
final TwoPhaseIterator twoPhase = s.twoPhaseIterator();
if (twoPhase == null) {
match = s.iterator().advance(doc) == doc;
} else {
match = twoPhase.approximation().advance(doc) == doc && twoPhase.matches();
}
if (match) {
assert s.score() == 0f : "score must be 0";
return Explanation.match(0f, "Match on id " + doc);
} else {
return Explanation.match(0f, "No match on id " + doc);
}
}
@Override
public Scorer scorer(LeafReaderContext context) throws IOException {
return new ConstantScoreScorer(this, 0f, scoreMode, getTwoPhaseIterator(context));
}
};
}
use of org.apache.lucene.search.TwoPhaseIterator in project crate by crate.
the class ShardSplittingQuery method createWeight.
@Override
public Weight createWeight(IndexSearcher searcher, ScoreMode scoreMode, float boost) {
return new ConstantScoreWeight(this, boost) {
@Override
public String toString() {
return "weight(delete docs query)";
}
@Override
public Scorer scorer(LeafReaderContext context) throws IOException {
LeafReader leafReader = context.reader();
FixedBitSet bitSet = new FixedBitSet(leafReader.maxDoc());
Terms terms = leafReader.terms(RoutingFieldMapper.NAME);
Predicate<BytesRef> includeInShard = ref -> {
int targetShardId = OperationRouting.generateShardId(indexMetadata, Uid.decodeId(ref.bytes, ref.offset, ref.length), null);
return shardId == targetShardId;
};
if (terms == null) {
// by ID and parent and nested all have the same id.
assert indexMetadata.isRoutingPartitionedIndex() == false;
findSplitDocs(IdFieldMapper.NAME, includeInShard, leafReader, bitSet::set);
} else {
if (indexMetadata.isRoutingPartitionedIndex()) {
// this is the heaviest invariant. Here we have to visit all docs stored fields do extract _id and _routing
// this this index is routing partitioned.
Visitor visitor = new Visitor(leafReader);
TwoPhaseIterator twoPhaseIterator = new RoutingPartitionedDocIdSetIterator(visitor);
return new ConstantScoreScorer(this, score(), scoreMode, twoPhaseIterator);
} else {
// in the _routing case we first go and find all docs that have a routing value and mark the ones we have to delete
findSplitDocs(RoutingFieldMapper.NAME, ref -> {
int targetShardId = OperationRouting.generateShardId(indexMetadata, null, ref.utf8ToString());
return shardId == targetShardId;
}, leafReader, bitSet::set);
// with a routing value from the next iteration an delete / select based on the ID.
if (terms.getDocCount() != leafReader.maxDoc()) {
// this is a special case where some of the docs have no routing values this sucks but it's possible today
FixedBitSet hasRoutingValue = new FixedBitSet(leafReader.maxDoc());
findSplitDocs(RoutingFieldMapper.NAME, ref -> false, leafReader, hasRoutingValue::set);
IntConsumer bitSetConsumer = bitSet::set;
findSplitDocs(IdFieldMapper.NAME, includeInShard, leafReader, docId -> {
if (hasRoutingValue.get(docId) == false) {
bitSetConsumer.accept(docId);
}
});
}
}
}
return new ConstantScoreScorer(this, score(), scoreMode, new BitSetIterator(bitSet, bitSet.length()));
}
@Override
public boolean isCacheable(LeafReaderContext ctx) {
// anyway.
return false;
}
};
}
use of org.apache.lucene.search.TwoPhaseIterator in project crate by crate.
the class ProfileScorer method twoPhaseIterator.
@Override
public TwoPhaseIterator twoPhaseIterator() {
if (isConstantScoreQuery) {
return scorer.twoPhaseIterator();
}
final TwoPhaseIterator in = scorer.twoPhaseIterator();
if (in == null) {
return null;
}
final DocIdSetIterator inApproximation = in.approximation();
final DocIdSetIterator approximation = new DocIdSetIterator() {
@Override
public int advance(int target) throws IOException {
advanceTimer.start();
try {
return inApproximation.advance(target);
} finally {
advanceTimer.stop();
}
}
@Override
public int nextDoc() throws IOException {
nextDocTimer.start();
try {
return inApproximation.nextDoc();
} finally {
nextDocTimer.stop();
}
}
@Override
public int docID() {
return inApproximation.docID();
}
@Override
public long cost() {
return inApproximation.cost();
}
};
return new TwoPhaseIterator(approximation) {
@Override
public boolean matches() throws IOException {
matchTimer.start();
try {
return in.matches();
} finally {
matchTimer.stop();
}
}
@Override
public float matchCost() {
return in.matchCost();
}
};
}
use of org.apache.lucene.search.TwoPhaseIterator in project OpenGrok by OpenGrok.
the class CustomSloppyPhraseScorerTest method test.
public static void test(final int slop, final int offset, final String[] terms, final Integer[] expectedPositions) throws IOException {
Directory dir = new ByteBuffersDirectory();
try (IndexWriter iw = new IndexWriter(dir, new IndexWriterConfig())) {
Document doc = new Document();
doc.add(new TextField("test", "zero one two three four five six seven eight nine ten", Field.Store.NO));
iw.addDocument(doc);
}
CustomPhraseQuery query = new CustomPhraseQuery(slop, "test", terms);
query.setOffset(offset);
try (IndexReader ir = DirectoryReader.open(dir)) {
IndexSearcher is = new IndexSearcher(ir);
Weight w = query.createWeight(is, ScoreMode.COMPLETE_NO_SCORES, 1);
LeafReaderContext context = ir.getContext().leaves().get(0);
Scorer scorer = w.scorer(context);
TwoPhaseIterator it = scorer.twoPhaseIterator();
int correctDoc = -1;
int docId;
while ((docId = it.approximation().nextDoc()) != DocIdSetIterator.NO_MORE_DOCS) {
if (it.matches()) {
correctDoc = docId;
}
}
BitIntsHolder bs = (BitIntsHolder) ((PhraseScorer) scorer).getPositions(correctDoc);
assertThat(toSet(bs), contains(expectedPositions));
}
}
Aggregations