Lucene实践之Query

检索过程中可能会面临各种各样的复杂条件检索,今天学习一下lucene各种Query,并通过多个Query的合并使用实现多条件的检索。

Game Starts

参考文档

  1) Package org.apache.lucene.search Description

  2) Lucene整理4-各种Query(转)

依赖的jar包

  1)lucene-core.jar

  2)lucene-analyzer-common

  3)lucene-queryParser

主要的类

  1)Term

Term表示的就是一个词,这里的词并不是我们生活中所谓的词语,而是lucene创建索引时所做的分词,使用的分词器不同这里对词的划分也就不同。
例如‘爸爸去哪儿’,我使用IKAnalyzer分词后为‘爸爸’‘去哪儿’,这里我用‘爸爸’‘去哪儿’匹配都可以匹配,但是用‘爸爸去哪儿’‘爸爸去’‘爸’等都是无法匹配的。
Term有三种构造方法。常用的有两种1、public Term(String fld,  BytesRef bytes); 2、public Term(String fld, String text);
注意的是参数不要为空,BytesRef String都是传递的引用,所以应用的对象在后面不要发生改变,话说回来,让String引用的对象发生改变还是挺费劲的。 

  2)TermQuery

TermQuery是最简单最常用的一个Query的实现。TermQuery匹配包含指定的Term的Document。简单的构造方法TermQuery tq = new TermQuery(new Term("fieldName", "term"));匹配分filedName中包含term的,注意是包含,不是完全匹配,想要完全匹配怎么办?构建索引的是对这个field不分词就行了,还是要记住什么是Term.

  3)BooleanQuery

当将多个TermQuery合并到一起时,可以使用BooleanQuery,通过BooleanClause参数决定TermQuery之间的合并关系.BooleanClause有三个值
  1、MUST 该TermQuery必须满足
  2、SHOULD 多个TermQuery至少满足一个
  3、MUST_NOT TermQuery必须不满足
当然BooleanQuery并不局限于TermQuery的合并,和可以和其他的Query合作。

  4)PhrasesQuery

PhrasesQuery 是另一个常用的Query。匹配多个Term,通过坡度(slop)来指定任意两个指定的Term之间最多可以像个几个Term。MultiPhraseQuery 是一个更常见的PhraseQuery的形式,可以实现更为复杂的Term排列。具体例子【Always Be Coding】会给出。

  5)TermRangeQuery

TermRangeQuery,很明显是按Term的范围来匹配。当然指定的field是可以比较的。特别说明数值类的不可以用这个Query,使用数值类特有的NumericRangeQuery。

  6)NumericRangeQuery

NumericRangeQuery 匹配数值范围。要想使得NumericRangeQuery起作用,构建索引是也要使用数值域(IntField, LongField, FloatField, or DoubleField)

  7)QueryParser

QueryParser是使用特定分词器解析query。将query分成若干个Term,然后去和Document匹配。多个Term之间的关系有点类似于BoolenQuery的 BooleanClause.SHOULD,但是匹配的term数会影响到结果的排序

  8)MultiFieldQueryParser

MultiFieldQueryParser,很明显是同时对多个域进行分析。
MultiFieldQueryParser.parse(Version matchVersion, String[] queries, String[] fields, Analyzer analyzer)
MultiFieldQueryParser.parse(Version matchVersion, String[] queries, String[] fields, BooleanClause.Occur[] flags, Analyzer analyzer)
MultiFieldQueryParser.parse(Version matchVersion, String query, String[] fields, BooleanClause.Occur[] flags, Analyzer analyzer)
其中数组的长度一定要对应好

Always Be Coding

 1 package lucene;
 2
 3 import java.io.File;
 4 import java.io.IOException;
 5
 6 import org.apache.lucene.analysis.Analyzer;
 7 import org.apache.lucene.document.Document;
 8 import org.apache.lucene.index.DirectoryReader;
 9 import org.apache.lucene.index.IndexReader;
10 import org.apache.lucene.index.Term;
11 import org.apache.lucene.queryparser.classic.MultiFieldQueryParser;
12 import org.apache.lucene.queryparser.classic.ParseException;
13 import org.apache.lucene.queryparser.classic.QueryParser;
14 import org.apache.lucene.search.BooleanClause;
15 import org.apache.lucene.search.BooleanClause.Occur;
16 import org.apache.lucene.search.BooleanQuery;
17 import org.apache.lucene.search.IndexSearcher;
18 import org.apache.lucene.search.MultiPhraseQuery;
19 import org.apache.lucene.search.NumericRangeQuery;
20 import org.apache.lucene.search.PhraseQuery;
21 import org.apache.lucene.search.Query;
22 import org.apache.lucene.search.ScoreDoc;
23 import org.apache.lucene.search.TermQuery;
24 import org.apache.lucene.search.TermRangeQuery;
25 import org.apache.lucene.search.TopDocs;
26 import org.apache.lucene.store.FSDirectory;
27 import org.apache.lucene.util.BytesRef;
28 import org.apache.lucene.util.Version;
29 import org.wltea.analyzer.lucene.IKAnalyzer;
30
31 public class Searcher {
32     public static void main(String[] args) throws IOException, ParseException {
33         IndexSearcher indexSearcher;
34         Analyzer anlyzer = new IKAnalyzer(true);;
35         long start = System.currentTimeMillis();
36         IndexReader indexReader = DirectoryReader.open(FSDirectory.open(new File("/home/erbin/Documents/data/index")));
37         indexSearcher = new IndexSearcher(indexReader);
38         BooleanQuery booleanQuery = new BooleanQuery();
39         QueryParser parser = new QueryParser(Version.LUCENE_46, "title", anlyzer);
40         Query query = parser.parse("爸爸");
41         booleanQuery.add(query, Occur.MUST);
42         TermQuery termQuery = new TermQuery(new Term("city","北京"));
43         booleanQuery.add(termQuery, Occur.MUST);
44         PhraseQuery phraseQuery = new PhraseQuery();
45         phraseQuery.setSlop(1);
46         phraseQuery.add(new Term("name","爸爸"));
47         phraseQuery.add(new Term("name","妈妈"));
48         booleanQuery.add(phraseQuery, Occur.MUST_NOT);
49         MultiPhraseQuery multiPhrasequery = new MultiPhraseQuery();
50         multiPhrasequery.add(new Term("name","爸爸"));//前缀
51         Term t1 = new Term("name", "去哪儿");//爸爸去哪儿 或者 爸爸ni
52         Term t2 = new Term("name", "到哪儿");
53         multiPhrasequery.add(new Term[]{t1, t2});//组成:爸爸去哪儿,爸爸到哪儿
54         booleanQuery.add(multiPhrasequery, Occur.SHOULD);
55         Query numericRangeQuery = NumericRangeQuery.newIntRange("name", 0, 4, false, false);
56         booleanQuery.add(numericRangeQuery, Occur.SHOULD);
57         Query termRangeQuery = new TermRangeQuery("name", new BytesRef("20100101"), new BytesRef("20101231"), false, false);
58         booleanQuery.add(termRangeQuery, Occur.SHOULD);
59         Query multiFieldQueryParser = MultiFieldQueryParser.parse(Version.LUCENE_46,                                             "爸爸",                                             new String[]{"name","content"},                                             new BooleanClause.Occur[]{Occur.MUST,Occur.MUST_NOT} ,                                            anlyzer);
60         booleanQuery.add(multiFieldQueryParser, Occur.SHOULD);
61         TopDocs results = indexSearcher.search(booleanQuery, 10);
62         ScoreDoc[] hits = results.scoreDocs;
63         int totalHits = results.totalHits;
64         for(int i = 0; i < totalHits; i++) {
65             Document doc = indexSearcher.doc(hits[i].doc);
66             System.out.println("["+doc.get("title")+"]");
67         }
68         long end = System.currentTimeMillis();
69         System.out.println(end - start);
70     }
71 }

TO BE CONTINUED……

时间: 2024-10-05 04:59:23

Lucene实践之Query的相关文章

Lucene实践之中文分词IKAalyzer

做检索怎么都绕不过中文分词去,学习一下用IKAnalyzer分词器做中文分词. Game Starts 参考文档 1) 中文分词之Java实现使用IK Analyzer实现 2) IKAnalyzer 独立使用 配置扩展词典 依赖jar包 1) IKAnalyzer2012FF_u1.jar 最好使用这个版本下面说 [百度网盘下载] 2) IKAnalyzer.cfg.xml [百度网盘下载] 3) keyWord.dic,stopWord.dic 字典 主要的类 1) IKAnalyzer ,

Lucene实践之SearchFile

上一篇学习了构建索引,这一篇来检索索引,同样是基础的用法. 准备工作 参考文档 1) http://lucene.apache.org/core/4_9_0/demo/src-html/org/apache/lucene/demo/SearchFiles.html 依赖jar包 上篇Lucene实践之SearchFile中的jar包即可. 主要的类 1) IndexReader , 读取索引文件 2) IndexSearcher , 核心类执行检索 3) QueryParser , 用于解析用户

Lucene中的 Query对象

"Lucene中的 Query对象": 检 索前,需要对检索字符串进行分析,这是由queryparser来完成的.为了保证查询的正确性,最好用创建索引文件时同样的分析器. queryparser解析字符串时,可以指定查询域,实际可以在字符串中指定一个或多个域.例如:“info:电视台 and id:3329”,“info:电视台”,“电视台”,假如不指定默认域,就会在默认域查询. queryparser调用静态方法parse后会返回query的实例,原子查询.例如:“info:电视台

Lucene Query Term Weighting

方法 1 public static Query TermWeighting(Query tquery,Map<String,Float>term2weight){ 2 BooleanQuery nquery = new BooleanQuery(); 3 Set<Term> terms = new HashSet<Term>(); 4 tquery.extractTerms(terms); 5 for(Term itr : terms){ 6 float weight

CSS media query应用中的层叠特性使用最佳实践

media query是css3规范中引入的,它提供了一种responsive design的基础机制:浏览器在不同size的设备中将以不同样式展现网页,这就给一个网页能够适应不同device一种可能.在实际使用中,我常常碰到以下问题:为什么media query的rule不起作用?很有可能和你的media query所处的位置有关,也很有可能和media query中的selector权重不 如外面的targeting到相同元素的css权重有关,比如: @media screen and (m

lucene 查询的使用

各种查询 方式一:使用QueryParser与查询语法.(会使用分词器) MultiFieldQueryParser 查询字符串 ------------------------> Query对象 例如: 上海 AND 天气 上海 OR 天气 上海新闻 AND site:news.163.com ... 方式二: 直接创建Query的实例(子类的),不会使用分词器 new TermQuery(..); new BooleanQuery(..); 1 package cn.itcast.i_que

Lucene 搜索功能

搜索过程 图解: 主要 API: IndexSearcher:    //所有搜索都通过 IndexSearcher 进行,他们将调用该类中重载的 search() 方法 Query:            //封装某种查询类型的具体子类,Query 实例将会被传递给 IndexSearcher 的 search() 方法 QueryParser:      //将用户输入的查询表达式处理成各种具体的 Query 对象 TopDocs:          //保存由 IndexSearcher.

Lucene 3.0 输出相似度

http://www.cnblogs.com/ibook360/archive/2011/10/19/2217638.html Lucene3.0之结果排序(原理篇) 传统上,人们将信息检索系统返回结果的排序称为"相关排序" (relevance ranking) ,隐含其中各条目的顺序反映结果和查询的相关程度. 1. 基本排序原理 ①     向量空间模型 Gerald Salton 等在 30 多年前提出的"向量空间模型" (Vector Space Model

lucene quickstart-基本检索

有了上一篇建立的索引,就可以进行检索了. 数据库查询使用SQL,lucene检索使用Query. lucene提供了一个IndexSearcher类,检索的功能通过这个类完成,其构造方法需要一个IndexReader对象.IndexReader用于读取索引库Directory. IndexSearcher有许多重构的方法,其中返回值为TopDocs类型的为最简单的.本文使用这个方法进行演示.TopDocs保存检索结果,其中的scoreDocs属性保存了记录的docId及评分,根据docId就可以