Allow FST read method to also recycle the output value when traversing FST [LUCENE-5584]
- Dominant language
- Java
- Stars
- 3.6k
- Forks
- 1.4k
- Avg merge
- 2d 11h
- Merged PRs (30d)
- 88
Description
The FST class heavily reuses Arc instances when traversing the FST. The output of an Arc however is not reused. This can especially be important when traversing large portions of a FST and using the ByteSequenceOutputs and CharSequenceOutputs. Those classes create a new byte[] or char[] for every node read (which has an output).
In our use case we intersect a lucene Automaton with a FST<BytesRef> much like it is done in org.apache.lucene.search.suggest.analyzing.FSTUtil.intersectPrefixPaths() and since the Automaton and the FST are both rather large tens or even hundreds of thousands of temporary byte array objects are created.
One possible solution to the problem would be to change the org.apache.lucene.util.fst.Outputs class to have two additional methods (if you don't want to change the existing methods for compatibility):
```Java
/** Decode an output value previously written with {`@link`
* #write(Object, DataOutput)} reusing the object passed in if possible */
public abstract T read(DataInput in, T reuse) throws IOException;
/** Decode an output value previously written with {`@link`
* #writeFinalOutput(Object, DataOutput)}. By default this
* just calls {`@link` #read(DataInput)}. This tries to reuse the object
* passed in if possible */
public T readFinalOutput(DataInput in, T reuse) throws IOException {
return read(in, reuse);
}
```
The new methods could then be used in the FST in the readNextRealArc() method passing in the output of the reused Arc. For most inputs they could even just invoke the original read(in) method.
If you should decide to make that change I'd be happy to supply a patch and/or tests for the feature.
---
Migrated from [LUCENE-5584](https://issues.apache.org/jira/browse/LUCENE-5584) by Christian Ziech, updated May 15 2014
Attachments: [fst-itersect-benchmark.tgz](https://apache.github.io/lucene-jira-archive/attachments/LUCENE-5584/fst-itersect-benchmark.tgz)
Contributor guide
Research direction
Start with org.apache.lucene.util.fst.Outputs and the FST.readNextRealArc() method, then inspect ByteSequenceOutputs, CharSequenceOutputs, and FSTUtil.intersectPrefixPaths(). Verify how reused Arc output values are decoded and use the attached intersection benchmark or relevant FST tests to confirm reduced temporary allocations without changing traversal behavior.
Written by the indexing model from the issue text.
Assessment
- Tech stack
- java
- Domain
- search
- Issue type
- Feature
- Difficulty
- 4/5
- Estimated time
- 3-5 days
- Activity status
- Stale
- Clarity
- Mostly clear
- Newbie friendliness
- 45/100