我想要计算TF-以色列国防军的分数,这是标准化的字段规范,在字段COMBINED_FIELD中的每个术语的各种文件是通过Lucene找到的。正如您在下面的代码中所看到的,我能够获得文档字段中每个术语的词频,我也可以获得文档频率,但我无法在查询时找到获取该字段规范的方法。到目前为止,我发现的所有方法都依赖于只存在于较旧的Lucene版本中的方法,而对于Lucene 6则不然。方法可能是使用LeafReader,但我没有找到获取它的实例的方法。
您知道我如何才能获得每个文档的字段COMBINED_FIELD规范吗?
或者我可以使用termVector.size()替换字段长度?“大小”()是否考虑了每个术语的发生次数,还是每个术语只计算一次?
提前感谢!
IndexSearcher iSearcher = null;
ScoreDoc[] docs = null;
try {
iSearcher = this.searchManager.acquire();
IndexReader reader = iSearcher.getIndexReader();
MultiFieldQueryParser parser = new MultiFieldQueryParser(this.getSearchFields(), this.queryAnalyzer);
parser.setDefaultOperator(QueryParser.Operator.OR);
Query query = parser.parse(QueryParser.escape(searchString));
docs = iSearcher.search(query, maxSearchResultNumber).scoreDocs;
for(int i=0; i < docs.length; i++) {
Terms termVector = reader.getTermVector(docs[i].doc, COMBINED_FIELD);
TermsEnum itr = termVector.iterator();
BytesRef term = null;
PostingsEnum postings = null;
while((term = itr.next()) != null){
String termText = term.utf8ToString();
postings = itr.postings(postings, PostingsEnum.FREQS);
postings.nextDoc();
int tf = postings.freq();
int docFreq = reader.docFreq(new Term(COMBINED_FIELD, term));
//HERE I WANT TO GET THE FIELD LENGTH OF THE CURRENT DOCUMENT
}
}
} catch (Exception e) {
// TODO Auto-generated catch block
e.printStackTrace();
} finally {
try {
this.searchManager.release(iSearcher);
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}Alternively,是否有一种方法可以直接从Lucene获得字段的每个项的TF-IDF或BM25值??
发布于 2017-09-04 08:26:54
Lucene在org.apache.lucene.search.similarities.Similarity#computeNorm方法中内部计算索引期间的规范,然后对其进行编码并存储在.nvm文件中的磁盘上。稍后,在查询/评分期间,只对其进行解码。
我认为,在Lucene中以编程方式完成这一任务的一种可能方法是扩展相似类,并在索引期间以某种方式获取这些信息,并将其存储在某个地方。我听起来不是最好的方法,但至少有一些东西。
另一方面,BM25Similarity以这种方式计算长度:
discountOverlaps ? state.getLength() - state.getNumOverlap() : state.getLength();其中getLength()是字段中的术语数,您可以像在示例中一样,通过在while中迭代来计算这些项。
https://stackoverflow.com/questions/46026674
复制相似问题