Lucene是apache組織的一個用java實(shí)現(xiàn)全文搜索引擎的開源項(xiàng)目。
其功能非常的強(qiáng)大,api也很簡單。總得來說用Lucene來進(jìn)行建立
和搜索和操作數(shù)據(jù)庫是差不多的(有點(diǎn)像),Document可以看作是
數(shù)據(jù)庫的一行記錄,F(xiàn)ield可以看作是數(shù)據(jù)庫的字段。用lucene實(shí)
現(xiàn)搜索引擎就像用JDBC實(shí)現(xiàn)連接數(shù)據(jù)庫一樣簡單。
Lucene2.0,它與以前廣泛應(yīng)用和介紹的Lucene
Lucene2.0的下載地址是http://apache.justdn.org/lucene/java/
大家先看一個例子,通過這個例子來對
lucene
的一個大概的認(rèn)識。
一個
Junit
測試用例:
(
為了讓代碼清晰好看,我們將異常都拋出
)
a)???
這是一個建立文件索引的例子
public
void
testIndexHello()
throws
IOException
??? {
??????? Date date1 =
new
Date();
?
???????
//
可以說是創(chuàng)建一個新的寫入工具
???????
//
第一個參數(shù)是要索引建立在哪個目錄里
???????
//
第二個參數(shù)是新建一個文本分析器,這里用的是標(biāo)準(zhǔn)的大家也可以自己寫一個
???????
//
第三個參數(shù)如果是true,在建立索引之前先將c:\\index目錄清空。
??????? IndexWriter writer =
new
IndexWriter(
"c:\\index"
,
new
StandardAnalyzer(),
true
);
???????
//?????
這個是數(shù)據(jù)源的文件夾
??????? File file =
new
File(
"c:\\file"
);
???????
/**
???????
?
*
例子主要是將C:\\file目錄下的文件的內(nèi)容進(jìn)行建立索引,將文件路徑作為搜索內(nèi)容的附屬.
???????
?
*/
???????
???????
if
(file.isDirectory())
??????? {
??????????? String[] fileList = file.list();
???????????
for
(
int
i = 0; i < fileList.
length
; i++)
??????????? {
//?????????????
建立一個新的文檔,它可以看作是數(shù)據(jù)庫的一行記錄
??????????????? Document doc =
new
Document();
??????????????? File f =
new
File(file,
???????????????
??????? fileList[i]);
??????????????? Reader reader =
new
BufferedReader(
new
FileReader(f));
??????????????? doc.add(
new
Field(
"file"
,reader));
//
為doument添加field
??????????????? doc.add(
new
Field(
"path"
,f.getAbsolutePath(),Field.Store.
YES
,Field.Index.
NO
));
??????????????? writer.addDocument(doc);
??????????? }
???????????
??????? }
??????? writer.close();
//
這一步是必須的,只有這樣數(shù)據(jù)才會被寫入索引的目錄里
??????? Date date2 =
new
Date();
??????? System.
out
.println(
"
用時"
+(date2.getTime()-date1.getTime())+
"
毫秒"
);
}
注意:因?yàn)榻⑺饕緛砭褪琴M(fèi)時,所以說最后輸出的用時會比較長,請不要奇怪。
b)
一個通過索引來全文檢索的例子
public
void
HelloSearch()
throws
IOException, ParseException
??? {
??????? IndexSearcher indexSearcher =
new
IndexSearcher(
"c:\\index"
);
//
和上面的IndexWriter一樣是一個工具
??????? QueryParser queryParser =
new
QueryParser(
"file"
,
//
這是一個分詞器
???????????????
new
StandardAnalyzer());
??????? BufferedReader br =
new
BufferedReader(
new
InputStreamReader(System.
in
));
??????? Query query = queryParser.parse(br.readLine());
//
這個地方Query是抽象類大家也注意一下,下面會講到的
??????? Hits hits = indexSearcher.search(query);
??????? Document doc =
null
;
??????? System.
out
.print(
"
正搜索................"
);
???????
for
(
int
i = 0; i < hits.length(); i++)
??????? {
??????????? doc = hits.doc(i);
??????????? System.
out
.println(
"
內(nèi)容是:"
+doc.get(
"file"
));
//
注意這里輸出的是什么
??????????? System.
out
.println(
"
文件的路徑是:"
+ doc.get(
"path"
));
??????? }
??? }
通過上面的兩個例子應(yīng)該可以看出Lucene還是比較簡單的。
運(yùn)行一下上面的兩個例子,大家可能會說怎么doc.get(
“
file
”
);
返回的是空呢,我們馬上會講到。
下面講一下索引的建立
其實(shí)從上面的例子就可以看出建立索引就用到Document,IndexWriter,Field。
最簡單的步驟就是:
首先分別new 一個Document,IndexWriter,Field
然后用Doument.add()方法加入Field,
其次用IndexWrtier.addDocument()方法加入Document。
最后調(diào)用一下IndexWriter.close()方法關(guān)閉輸入索引,這一步非常的重要只有調(diào)用這個方法索引才會被寫入索引的目錄里,而這是被很多初學(xué)的人所忽略的。
Document
沒有什么好介紹的,把它的作用看成數(shù)據(jù)庫中的一行記錄就行。
Field
是一個比較重要的也是比較復(fù)雜的:
看一下它的構(gòu)造函數(shù)有5個:
Field
(String?name, byte[]?value, Field.Store?store)
Field
(String?name, Reader?reader)
Field
(String?name, Reader?reader, Field.TermVector?termVector)
Field
(String?name, String?value, Field.Store?store, Field.Index?index)
Field
(String?name, String?value, Field.Store?store, Field.Index?index, Field.TermVector?termVector)
在Field中有三個內(nèi)部類:Field.Index,Field.Store,Field.termVector,而構(gòu)造函數(shù)也用到了它們。
注意:
termVector
是Lucene 1.4
新增的它提供一種向量機(jī)制來進(jìn)行模糊查詢的這個不常用,默認(rèn)是false不過是什么對于一般查詢無影響。
它們的不同的組合,在全文檢索中有著不同的作用。看看下面的表吧:
Field.Index |
Field.Store |
說明 |
|
文章的標(biāo)題或內(nèi)容(如果是內(nèi)容的話不能太長)是可以被搜索的 |
|
文章的標(biāo)題或內(nèi)容(內(nèi)容可以很長)也是可以被看過的 |
||
這是不能被搜索的,它只是被搜索內(nèi)容的附屬物。如URL等 |
||
|
不被分詞,它作為一個整體被搜索,搜一部分是搜不出來的 |
|
沒有這種用法 |
而對于
Field
(String?name, Reader?reader)
Field
(String?name, Reader?reader, Field.TermVector?termVector)
他們是Field.Index.TOKENIZED和Field.Store.NO的。這就是為什么我們在上面的例子中會出現(xiàn)文章的內(nèi)容為null了。因?yàn)樗皇潜凰饕耍]有被存儲下來。如果一定要看到文章的內(nèi)容的話可以通過文章的路徑得到畢竟文章的路徑是作為搜索的附屬物被搜索出來了。而我們在Web開發(fā)的時候一般是將大數(shù)據(jù)放在數(shù)據(jù)庫中,不會放在文件系統(tǒng)中,更不會放在索引目錄里,因?yàn)樗罅瞬僮鲿哟蠓?wù)器的負(fù)擔(dān)。
下面介紹一下IndexWriter:
它就是一個寫入索引的寫入器,它的任務(wù)比較簡單:
1.
用addDocument()將已經(jīng)準(zhǔn)備好寫入索引的document們加入
2.
調(diào)用close()將索引寫入索引目錄
先看一下它的構(gòu)造函數(shù):
IndexWriter
(Directory?d, Analyzer?a, boolean?create)
(未完)
|
|||||||||||||