今天开始接触Lucene搜索,Lucene是一个全文检索的框架,主要适用于搜索,这里的搜索不同于天龙八部私服数据库的查询。Lucene是建立索引然后存在你设置的路径或者内存中,然后当你输入条件的时候就会去索引文件检索查询。Lucene能够实现分词和查询结构高亮的功能,而且在其强大的天龙八部私服架构下全文检索的速度是比较快的。由于Lucene将数据分词后以索引方式存储,这就势必会占内存或空间(Lucene的索引存储一般有文件存储和内存存储2种方式),我们就会将不必要的东西不存储。而我们一般在使用Lucene和数据库结合的时候,像主键这些是要存的,就有利于我们在搜索的时候得到document对象同时也能得到存储在里面的主键,然后就可以通过主键获取数据库里面的数据。
接下来开始第一个Lucene程序,首先导入lucene-core.jar的包,Lucene基本所有重要的类都在core包中。
public class Test1 { private static Directory directory;static{ directory = new RAMDirectory(); }public static void main(String[] args) { Analyzer analyzer = new StandardAnalyzer(Version.LUCENE_35); IndexWriterConfig conf = new IndexWriterConfig(Version.LUCENE_35, analyzer); try { IndexWriter writer = new IndexWriter(directory, conf); Document doc = null; for(int i=1;i<=10;i++){ doc = new Document(); doc.add(new Field("name", "dlm"+i, Field.Store.YES, Field.Index.NOT_ANALYZED)); doc.add(new Field("pass", "wei dlm"+i, Field.Store.YES, Field.Index.ANALYZED)); writer.addDocument(doc); } doc = new Document(); doc.add(new Field("name", "sdlm", Field.Store.YES, Field.Index.NOT_ANALYZED)); writer.addDocument(doc); writer.commit(); IndexReader reader = IndexReader.open(directory); IndexSearcher searcher = new IndexSearcher(reader); TermQuery query = new TermQuery((new Term("name","dlm1"))); TopDocs topDocs = searcher.search(query, 20); ScoreDoc[] scoreDocs = topDocs.scoreDocs; for(ScoreDoc s:scoreDocs){ Document d = searcher.doc(s.doc); System.out.println(s.score+"===="+d.get("name")+"--"+d.get("pass")); } searcher.close(); reader.close(); writer.close(); } catch (IOException e) { // TODO Auto-generated catch block e.printStackTrace(); } } }
Directory对象是指管理索引文件存储位置的对象,RAMDirectory即表示将索引存储在内存,当然程序一运行结束,索引也就不存在了。然后创建分词器Analyzer表示分词器,在这里我使用的是标准分词器StandardAnalyzer,当然不同的分词器实现的功能也不是一样的(StopAnalyzer停词分词器,WhitespaceAnalyzer空格分词器),这些所有的分词器都是不支持中文分词的。然后创建IndexWriterConfig对象以此创建IndexWriter对象,IndexWriter主要用于存储索引,所以我们传入Directory和IndexWriterConfig。Document是存放待存储内容和待创建的索引对象,Field.Store.YES就是前面提到的是否存储,一一般内容不需要存储,这里存储指储存到天龙八部私服索引文件中,我们后面查询出来能够Document.get(name)获取到存储的值,设置NO即不能存储就不能取出值。Field.Index.ANALYZED 进行分词和索引,适用于文章天龙八部关系任务探秘标题、内容, Field.Index.NOT_ANALYZED 进行索引但是不分词,如身份证、ID,适用于精确搜索Field.Index.NOT_ANALYZED_NO_NORMS 既不分词也不存储normal信息, Field.Index.ANALYZED_NO_NORMS 分词不存储normal信息,Field.Index.NO 不分词不索引。添加完后需要提交commit,不然搜索不到索引。
IndexReader由open(Directory)即找到天龙八部私服索引的位置,IndexSearcher由reader获取得到,TermQuery表示精确查询,在这里输入dlm是查找不到结果的,searcher.search(query, 20);表示查找20条数据,topDocs.scoreDocs获得查询的结果集,然后遍历结果集,searcher.doc(s.doc);s.doc表示该查询结构所在的位置,然后得到document对象,就可以获得存储在天龙八部私服http://www.alishouhui.com索引文件中的值了。