2012-03-04 8 views
1

私はかなり大きなLucene.netインデックスを持っています(最新バージョンで作成 - 2.9)。それは約10億の文書を持っています。 〜70GBのHD空間が必要です。各文書は非常に小さく、文字列と整数の2つのフィールドだけです。Lucene.net:ソート時のメモリ不足

私は文字列フィールドで検索し、インデックスフィールドでソートします。つまり、ソートでクエリを実行しようとするとOutOfMemoryExceptionが発生します。コードは次のようになります。

var sort = new Sort(new SortField("frequency",SortField.INT,false)); 
var topDocs = searcher.Search(query, null, 1,sort); 

ソートを使用すると、どのクエリを使用しても問題ありません。クラッシュします。ここにスタックトレースがあります:

System.OutOfMemoryException: Exception of type 'System.OutOfMemoryException' was thrown. 
at Lucene.Net.Search.FieldCacheImpl.IntCache.CreateValue(IndexReader reader, Entry entryKey) 
at Lucene.Net.Search.FieldCacheImpl.Cache.Get(IndexReader reader, Entry key) 
at Lucene.Net.Search.FieldCacheImpl.GetInts(IndexReader reader, String field, IntParser parser) 
at Lucene.Net.Search.FieldCacheImpl.IntCache.CreateValue(IndexReader reader, Entry entryKey) 
at Lucene.Net.Search.FieldCacheImpl.Cache.Get(IndexReader reader, Entry key) 
at Lucene.Net.Search.FieldCacheImpl.GetInts(IndexReader reader, String field, IntParser parser) 
at Lucene.Net.Search.FieldComparator.IntComparator.SetNextReader(IndexReader reader, Int32 docBase) 
at Lucene.Net.Search.IndexSearcher.Search(Weight weight, Filter filter, Collector collector) 
at Lucene.Net.Search.IndexSearcher.Search(Weight weight, Filter filter, Int32 nDocs, Sort sort, Boolean fillFields) 
at Lucene.Net.Search.IndexSearcher.Search(Weight weight, Filter filter, Int32 nDocs, Sort sort) 
at Lucene.Net.Search.Searcher.Search(Query query, Filter filter, Int32 n, Sort sort) 

私はかなりLuceneを新しくしています。大量のデータをキャッシュしてメモリを使い果たしているように見えます。

更新: 実際、Luceneは私の場合は巨大な配列int [maxDoc]を作成しようとしています。

内部HitQueue(s)によって維持される用語値のキャッシュの使用をソートする。キャッシュは静的であり、ソートが実行される各フィールド名に対して、長さIndexReader.maxDoc()の整数または浮動小数点配列を含みます。言い換えれば、バイト単位でキャッシュのサイズは次のとおりです。 4 *のIndexReader.maxDoc()*(実際にソートするために使用される様々な分野の#)

私は何とかこの動作を変更することはできますか?

答えて

1

私は別のことをやった。私の結果がこのようにソートされることを常に望んでいることを認識して、私が本当に必要とするのは、Scoringに影響を与えることです。 Document.SetBoost()に整数パラメータの値を使用してインデックスを再構築したので、各ドキュメントのスコアはこのフィールドの値によって支配されます。 Luceneのデフォルトの動作は最高のスコアリングドキュメントを返すことであるため、私は必要なものを手に入れました。

1

いいえいいえ、この動作を変更することはできません。しかし、あなたが一番の結果にのみ関心があるので、あなたはカスタムCollectorを書くことができ、結果セット全体をソートせずにほとんどの結果を得ることができます(O(n)時間の整数配列のmaxを見つけるような)

Ifトップnの結果に興味がある場合は、PriorityQueueを使用できます。ここにはmy another answerの使い方を示すPriorityQueueCollector