私は実際に に対して異なる結果を得ていStandardAnalyzer
ます。次のコードを検討してください (Lucene v4 を使用):
public class Tokens {
private static void printTokens(String string, Analyzer analyzer) throws IOException {
System.out.println("Using " + analyzer.getClass().getName());
TokenStream ts = analyzer.tokenStream("default", new StringReader(string));
OffsetAttribute offsetAttribute = ts.addAttribute(OffsetAttribute.class);
CharTermAttribute charTermAttribute = ts.addAttribute(CharTermAttribute.class);
while(ts.incrementToken()) {
int startOffset = offsetAttribute.startOffset();
int endOffset = offsetAttribute.endOffset();
String term = charTermAttribute.toString();
System.out.println(term + " (" + startOffset + " " + endOffset + ")");
}
System.out.println();
}
public static void main(String[] args) throws IOException {
printTokens("foo-bar 1-2-3", new StandardAnalyzer(Version.LUCENE_40));
printTokens("foo-bar 1-2-3", new ClassicAnalyzer(Version.LUCENE_40));
QueryParser standardQP = new QueryParser(Version.LUCENE_40, "", new StandardAnalyzer(Version.LUCENE_40));
BooleanQuery q1 = (BooleanQuery) standardQP.parse("someField:(foo\\-bar\\ 1\\-2\\-3)");
System.out.println(q1.toString() + " # of clauses:" + q1.getClauses().length);
}
}
プリントの上:
Using org.apache.lucene.analysis.standard.StandardAnalyzer
foo (0 3)
bar (4 7)
1 (8 9)
2 (10 11)
3 (12 13)
Using org.apache.lucene.analysis.standard.ClassicAnalyzer
foo (0 3)
bar (4 7)
1-2-3 (8 13)
someField:foo someField:bar someField:1 someField:2 someField:3 # of clauses:5
StandardAnalyzer
したがって、上記のコードは、たとえば とは異なりClassicAnalyzer
、必要に応じて異なるトークンに分割する必要があることを証明して1-2-3
います。クエリの場合、スペースを含むすべてのキーワードをエスケープする必要があります。そうしないと、QP はこれが別の意味であると判断します。
クエリ文字列をエスケープしたくない場合は、(printTokens
上記の方法のように) 手動でいつでもトークン化できます。次に、各トークンを でラップし、TermQuery
すべての TermQueries を にスタックしますBooleanQuery
。