我无法弄清楚如何使短语查询起作用。它返回精确的mathes,但slop选项似乎没有什么区别。
这是我的代码:
static void Main(string[] args)
{
using (Directory directory = new RAMDirectory())
{
Analyzer analyzer = new StandardAnalyzer(Lucene.Net.Util.Version.LUCENE_29);
using (IndexWriter writer = new IndexWriter(directory, analyzer, true, IndexWriter.MaxFieldLength.UNLIMITED))
{
// index a few documents
writer.AddDocument(createDocument("1", "henry morgan"));
writer.AddDocument(createDocument("2", "henry junior morgan"));
writer.AddDocument(createDocument("3", "henry immortal jr morgan"));
writer.AddDocument(createDocument("4", "morgan henry"));
}
// search for documents that have "foo bar" in them
String sentence = "henry morgan";
IndexSearcher searcher = new IndexSearcher(directory, true);
PhraseQuery query = new PhraseQuery()
{
//allow inverse order
Slop = 3
};
query.Add(new Term("contents", sentence));
// display search results
List<string> results = new List<string>();
Console.WriteLine("Looking for \"{0}\"...", sentence);
TopDocs topDocs = searcher.Search(query, 100);
foreach (ScoreDoc scoreDoc in topDocs.ScoreDocs)
{
var matchedContents = searcher.Doc(scoreDoc.Doc).Get("contents");
results.Add(matchedContents);
Console.WriteLine("Found: {0}", matchedContents);
}
}
private static Document createDocument(string id, string content)
{
Document doc = new Document();
doc.Add(new Field("id", id, Field.Store.YES, Field.Index.NOT_ANALYZED));
doc.Add(new Field("contents", content, Field.Store.YES, Field.Index.ANALYZED, Field.TermVector.WITH_POSITIONS_OFFSETS));
return doc;
}
我认为除id = 3的文档之外的所有选项都应匹配,但只有第一个选项匹配。我错过了什么吗?
答案 0 :(得分:2)
在Lucene In Action 2nd中, 3.4.6按短语搜索:PhraseQuery 。
PhraseQuery使用此信息来查找术语在一定距离内的文档
当然,一个简单的TermQuery可以找到这个文档 知道这些单词中的任何一个,但在这种情况下我们只需要文档 有短语,其中的单词是完全并排的 (快速狐狸)或中间有一个词(快速[无关]狐狸)
因此,PhraseQuery实际上是在术语之间使用的,本章中的示例代码也证明了这一点。当你使用StandardAnalyzer时,&#34; henry morgan&#34; 分析后将是亨利和摩根。因此,你不能添加&#34;亨利摩根&#34;作为一个术语
/*
Sets the number of other words permitted between words
in query phrase.If zero, then this is an exact phrase search.
*/
public void setSlop(int s) { slop = s; }
setSlop的定义可以进一步解释这种情况。 在你的代码稍作修改之后,我就把它钉了。
// code in Scala
val query = new PhraseQuery();
query.setSlop(3)
List("henry", "morgan").foreach { word =>
query.add(new Term("contents", word))
}
在这种情况下,四个文件都将匹配。如果您有任何进一步的问题,我建议您阅读Lucene In Action 2nd中的那一章。 这可能有所帮助。