-
Notifications
You must be signed in to change notification settings - Fork 1.4k
Enable Block-Max WAND dynamic pruning for FunctionScoreQuery via DocValuesSkipper (+422% QPS) #16431
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Open
rajat315315
wants to merge
20
commits into
apache:main
Choose a base branch
from
rajat315315:feature/function-score-wand-skip-index
base: main
Could not load branches
Branch not found: {{ refName }}
Loading
Could not load tags
Nothing to show
Loading
Are you sure you want to change the base?
Some commits from the old base branch may be removed from the timeline,
and old review comments may become outdated.
Open
Enable Block-Max WAND dynamic pruning for FunctionScoreQuery via DocValuesSkipper (+422% QPS) #16431
Changes from 8 commits
Commits
Show all changes
20 commits
Select commit
Hold shift + click to select a range
5eac48d
perf: implement advanceShallow and getMaxScore logic for FunctionScor…
rajat315315 fb8e293
Implement DocValuesSkipper WAND pruning for FunctionScoreQuery and ad…
rajat315315 29ef08c
Update benchmark to test indexSort
rajat315315 168517c
Update benchmark to use BooleanQuery disjunction base query
rajat315315 1222a4e
Set DEFAULT_SKIP_INDEX_INTERVAL_SIZE to 128
rajat315315 4a73cce
Keep DEFAULT_SKIP_INDEX_INTERVAL_SIZE at 4096 in FunctionScoreQuery PR
rajat315315 ad7c840
Commit benchmark class
rajat315315 21042fa
Add support for monotonically decreasing functions in DoubleValuesSource
rajat315315 aff2cf6
Fix EOF trailing newlines
rajat315315 1fa8c20
Deprecate 2-arg fromField and add Javadoc note per review
rajat315315 8f187e1
Using a custom homemade function without needing to specify inc/dec.
rajat315315 6dba6f7
Using Monotonicity as an Enum.
rajat315315 152ed7f
Removed deprecated method.
rajat315315 6a1cdb5
prek
rajat315315 b996adf
gradlew tidy
rajat315315 9e8f7c0
Added a change entry
rajat315315 40dd742
Modified change entry
rajat315315 315a4e0
Add test case for non-monotonic function score queries to verify they…
rajat315315 c9d50aa
Add testConstantLambdaMonotonicity to compare INCREASING, DECREASING,…
rajat315315 fddb47c
Assert equal scoreDocs array length across constant lambda queries
rajat315315 File filter
Filter by extension
Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Some comments aren't visible on the classic Files Changed page.
There are no files selected for viewing
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
137 changes: 137 additions & 0 deletions
137
...jmh/src/java/org/apache/lucene/benchmark/jmh/FunctionScoreWANDMainVsFeatureBenchmark.java
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,137 @@ | ||
| /* | ||
| * Licensed to the Apache Software Foundation (ASF) under one or more | ||
| * contributor license agreements. See the NOTICE file distributed with | ||
| * this work for additional information regarding copyright ownership. | ||
| * The ASF licenses this file to You under the Apache License, Version 2.0 | ||
| * (the "License"); you may not use this file except in compliance with | ||
| * the License. You may obtain a copy of the License at | ||
| * | ||
| * http://www.apache.org/licenses/LICENSE-2.0 | ||
| * | ||
| * Unless required by applicable law or agreed to in writing, software | ||
| * distributed under the License is distributed on an "AS IS" BASIS, | ||
| * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. | ||
| * See the License for the specific language governing permissions and | ||
| * limitations under the License. | ||
| */ | ||
|
|
||
| package org.apache.lucene.benchmark.jmh; | ||
|
|
||
| import java.io.IOException; | ||
| import java.util.Random; | ||
| import java.util.concurrent.TimeUnit; | ||
| import org.apache.lucene.document.Document; | ||
| import org.apache.lucene.document.Field; | ||
| import org.apache.lucene.document.NumericDocValuesField; | ||
| import org.apache.lucene.document.TextField; | ||
| import org.apache.lucene.index.DirectoryReader; | ||
| import org.apache.lucene.index.IndexReader; | ||
| import org.apache.lucene.index.IndexWriter; | ||
| import org.apache.lucene.index.IndexWriterConfig; | ||
| import org.apache.lucene.index.Term; | ||
| import org.apache.lucene.queries.function.FunctionScoreQuery; | ||
| import org.apache.lucene.search.BooleanClause; | ||
| import org.apache.lucene.search.BooleanQuery; | ||
| import org.apache.lucene.search.DoubleValuesSource; | ||
| import org.apache.lucene.search.IndexSearcher; | ||
| import org.apache.lucene.search.Query; | ||
| import org.apache.lucene.search.TermQuery; | ||
| import org.apache.lucene.search.TopDocs; | ||
| import org.apache.lucene.store.ByteBuffersDirectory; | ||
| import org.apache.lucene.store.Directory; | ||
| import org.openjdk.jmh.annotations.Benchmark; | ||
| import org.openjdk.jmh.annotations.BenchmarkMode; | ||
| import org.openjdk.jmh.annotations.Fork; | ||
| import org.openjdk.jmh.annotations.Level; | ||
| import org.openjdk.jmh.annotations.Measurement; | ||
| import org.openjdk.jmh.annotations.Mode; | ||
| import org.openjdk.jmh.annotations.OutputTimeUnit; | ||
| import org.openjdk.jmh.annotations.Param; | ||
| import org.openjdk.jmh.annotations.Scope; | ||
| import org.openjdk.jmh.annotations.Setup; | ||
| import org.openjdk.jmh.annotations.State; | ||
| import org.openjdk.jmh.annotations.TearDown; | ||
| import org.openjdk.jmh.annotations.Warmup; | ||
|
|
||
| /** | ||
| * JMH Micro-benchmark comparing actual FunctionScoreQuery search throughput | ||
| * on main branch vs feature/function-score-wand-skip-index branch over 1 Million Lucene index documents. | ||
| */ | ||
| @State(Scope.Benchmark) | ||
| @BenchmarkMode(Mode.Throughput) | ||
| @OutputTimeUnit(TimeUnit.SECONDS) | ||
| @Warmup(iterations = 2, time = 2) | ||
| @Measurement(iterations = 3, time = 3) | ||
| @Fork( | ||
| value = 1, | ||
| warmups = 1, | ||
| jvmArgsAppend = {"-Xmx8g", "-Xms8g"}) | ||
| public class FunctionScoreWANDMainVsFeatureBenchmark { | ||
|
|
||
| @State(Scope.Benchmark) | ||
| public static class BenchmarkState { | ||
|
|
||
| @Param({"1000000"}) | ||
| public int numDocs; | ||
|
|
||
| @Param({"true", "false"}) | ||
| public boolean indexSort; | ||
|
|
||
| @Param({"100"}) | ||
| public int topK; | ||
|
|
||
| public Directory dir; | ||
| public IndexReader reader; | ||
| public IndexSearcher searcher; | ||
| public Query functionScoreQuery; | ||
|
|
||
| @Setup(Level.Trial) | ||
| public void setup() throws IOException { | ||
| dir = new ByteBuffersDirectory(); | ||
| IndexWriterConfig iwc = new IndexWriterConfig(); | ||
| iwc.setRAMBufferSizeMB(256); | ||
| if (indexSort) { | ||
| iwc.setIndexSort(new org.apache.lucene.search.Sort(new org.apache.lucene.search.SortField("score_field", org.apache.lucene.search.SortField.Type.LONG, true))); | ||
| } | ||
|
|
||
| try (IndexWriter writer = new IndexWriter(dir, iwc)) { | ||
| Random random = new Random(42); | ||
| String[] terms = {"term_a", "term_b", "term_c", "term_d", "term_e"}; | ||
| for (int i = 0; i < numDocs; i++) { | ||
| Document doc = new Document(); | ||
| String chosenTerm = terms[random.nextInt(terms.length)]; | ||
| doc.add(new TextField("body", chosenTerm, Field.Store.NO)); | ||
| // Real-world Power-law / Zipfian score distribution (98% low scores, 2% high scores) | ||
| long scoreVal = (random.nextFloat() < 0.02f) ? (50000 + random.nextInt(50000)) : random.nextInt(100); | ||
| doc.add(new NumericDocValuesField("score_field", scoreVal)); | ||
| writer.addDocument(doc); | ||
| } | ||
| writer.commit(); | ||
| } | ||
|
|
||
| reader = DirectoryReader.open(dir); | ||
| searcher = new IndexSearcher(reader); | ||
|
|
||
| BooleanQuery.Builder bq = new BooleanQuery.Builder(); | ||
| bq.add(new TermQuery(new Term("body", "term_a")), org.apache.lucene.search.BooleanClause.Occur.SHOULD); | ||
| bq.add(new TermQuery(new Term("body", "term_b")), org.apache.lucene.search.BooleanClause.Occur.SHOULD); | ||
| bq.add(new TermQuery(new Term("body", "term_c")), org.apache.lucene.search.BooleanClause.Occur.SHOULD); | ||
| bq.add(new TermQuery(new Term("body", "term_d")), org.apache.lucene.search.BooleanClause.Occur.SHOULD); | ||
| bq.add(new TermQuery(new Term("body", "term_e")), org.apache.lucene.search.BooleanClause.Occur.SHOULD); | ||
| Query baseQuery = bq.build(); | ||
| DoubleValuesSource valueSource = DoubleValuesSource.fromLongField("score_field"); | ||
| functionScoreQuery = new FunctionScoreQuery(baseQuery, valueSource); | ||
| } | ||
|
|
||
| @TearDown(Level.Trial) | ||
| public void tearDown() throws IOException { | ||
| reader.close(); | ||
| dir.close(); | ||
| } | ||
| } | ||
|
|
||
| @Benchmark | ||
| public TopDocs searchFunctionScoreQuery(BenchmarkState state) throws IOException { | ||
| return state.searcher.search(state.functionScoreQuery, state.topK); | ||
| } | ||
| } |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Oops, something went wrong.
Oops, something went wrong.
Add this suggestion to a batch that can be applied as a single commit.
This suggestion is invalid because no changes were made to the code.
Suggestions cannot be applied while the pull request is closed.
Suggestions cannot be applied while viewing a subset of changes.
Only one suggestion per line can be applied in a batch.
Add this suggestion to a batch that can be applied as a single commit.
Applying suggestions on deleted lines is not supported.
You must change the existing code in this line in order to create a valid suggestion.
Outdated suggestions cannot be applied.
This suggestion has been applied or marked resolved.
Suggestions cannot be applied from pending reviews.
Suggestions cannot be applied on multi-line comments.
Suggestions cannot be applied while the pull request is queued to merge.
Suggestion cannot be applied right now. Please check back later.
Uh oh!
There was an error while loading. Please reload this page.