Luncene工作原理

2021-06-08 07:53:05 字數 3577 閱讀 1204

lucene是乙個高效能的全文檢索工具包,它使用的是倒排檔案索引結構。lucene可以對任何的資料做索引和搜尋.lucene不管資料來源是什麼格式,只要它能被轉化為文字的形式,就可以被lucene所分析利用.也就是說不管是msword, html,pdf還是其他什麼形式的檔案只要你可以從中抽取出文字形式的內容就可以被lucene所用.你就可以用lucene對它們進行索引以及搜尋.

該結構及相應的生成演算法如下:

0)設有兩篇文章1和2

a.我們現在有的是文章內容,即乙個字串,我們先要找出字串中的所有單詞,即分詞。英文單詞由於用空格分隔,比較好處理。中文單詞間是連在一起的需要特殊的分詞處理。

b.文章中的」in」, 「once」「too」等詞沒有什麼實際意義,中文中的「的」「是」等字通常也無具體含義,這些不代表概念的詞可以過濾掉

c.使用者通常希望查「he」時能把含「he」,「he」的文章也找出來,所以所有單詞需要統一大小寫。

d.使用者通常希望查「live」時能把含「lives」,「lived」的文章也找出來,所以需要把「lives」,「lived」還原成「live」

e.文章中的標點符號通常不表示某種概念,也可以過濾掉

在lucene中以上措施由analyzer類完成

經過上面處理後

guangzhou 1

he 2

i 1live 1,2

shanghai 2

tom 1

加上「出現頻率」和「出現位置」資訊後,我們的索引結構變為:

guangzhou 1[2] 3,6

he 2[1] 1

i 1[1] 4

live 1[2],2[1] 2,5,2

shanghai 2[1] 3

tom 1[1] 1

以live這行為例我們說明一下該結構:live在文章1中出現了2次,文章2中出現了一次,它的出現位置為「2,5,2」這表示什麼呢?我們需要結合文章號和出現頻率來分析,文章1中出現了2次,那麼「2,5」就表示live在文章1中出現的兩個位置,文章2中出現了一次,剩下的「2」就表示live是文章2中第2個關鍵字。

下面我們可以通過對該索引的查詢來解釋一下為什麼要建立索引。

假設要查詢單詞「live」,lucene先對詞典二元查詢、找到該詞,通過指向頻率檔案的指標讀出所有文章號,然後返回結果。詞典通常非常小,因而,整個過程的時間是毫秒級的。

而用普通的順序匹配演算法,不建索引,而是對所有文章的內容進行字串匹配,這個過程將會相當緩慢,當文章數目很大時,時間往往是無法忍受的。

示例介紹:

為作為輸入引數的資料夾下的所有txt型別的檔案做索引,做好的索引檔案放入index資料夾。示例是對txt型別的檔案做索引,對資料庫做索引用方法與此類似,只是資料的**不同。對檔案做索引,搜尋的時候返回的是檔名;對資料庫中的表做索引,則應返回主鍵值。

然後在索引的基礎上對檔案進行全文搜尋.

1. 

建立索引

indexwriter writer = newindexwriter("index", new standardanalyzer(), true);

indexdocs(writer, newsystem.io.fileinfo(args[0]));

writer.optimize();

writer.close();

indexwriter是對索引進行寫操作的乙個類,利用它可以建立乙個索引物件然後往其中新增檔案.需要注意它並不是唯一可以修改索引的類.在索引建好後利用其他類還可以對其進行修改.

建構函式第乙個引數是建立的索引所要放的資料夾的名字.第二個引數是乙個分析物件,主要用於從文字中抽取那些需要建立索引的內容,把不需要參與建索引的文字內容去掉.比如去掉一些athe之類的常用詞,還有決定是否大小寫敏感.不同的選項通過指定不同的分析物件控制.第三個引數用於確定是否覆蓋原有索引的.

第二步就是利用這個writer往索引中新增檔案.具體後面再說.

第三步進行優化.

第四步關閉writer.

下面具體看看第二步:

public static void indexdirectory(indexwriterwriter, fileinfo file)}}

//如果file是乙個.txt檔案

else if (file.extension == ".txt")}

private static void indexfile(fileinfo file, indexwriterwriter)

catch (filenotfoundexception fnfe)

}主要就是兩個函式乙個用於處理資料夾(不是為資料夾建立索引),乙個用於真正為檔案建立索引.

因此主要集中看一下indexfile這個方法.首先建立document物件,然後為document物件新增一些屬性field.你可以把document物件看成是虛擬檔案,將來將從此獲取資訊.而field則看成是描述此虛擬檔案的元資料(metadata).

其中field包括四個型別:

keywork

該型別的資料將不被分析,而會被索引並儲存儲存在索引中.

unindexed

該型別的資料不會被分析也不會被索引,但是會儲存在索引.

unstored

和unindexed剛好相反,被分析被索引,但是不被儲存.

text

和unstrored類似.如果值的型別為string還會被儲存.如果值的型別reader就不會被儲存和unstored一樣.

最後將每乙個document新增到索引當中.

需要注意的是索引不僅可以建立在檔案系統上,也可以建立在記憶體中.

例如indexwriter writer = new indexwriter("index", newstandardanalyzer(), true);

在第乙個引數不是指定資料夾的名字而是使用directory物件,並使用它的子類ramdirectory,就可以將索引建立在記憶體當中.

2. 

對索引進行搜尋

indexsearcher indexsearcher= newindexsearcher(indexdir);

query query = queryparser.parse(querystring,"contents",new standardanalyzer());

hits hits = indexsearcher.search(query);

//儲存

arraylist list = new arraylist();

for (int i = 0; i < hits.length(); i++)

searcher.close();

return list;

第一步利用indexsearcher開啟索引檔案用於後面搜尋,其中的引數是索引檔案的路徑.

第二步使用queryparser將可讀性較好的查詢語句(比如查詢的詞lucene,以及一些高階方式lucene and.net)轉化為lucene內部使用的查詢物件.

第三步執行搜尋.並將結果返回到hits集合.需要注意的是lucene並不是一次將所有的結果放入hits中而是採取一次放一部分的方式.出於空間考慮.

Luncene學習和使用

接觸了下lucene的公升級,這裡記錄從0學習lucene之路。公司從lucene 3.6公升級到當前最新的lucene 7.4.0,改動還是比較大的。這裡先分享下自己學習的幾個有料的部落格,以備以後學習 下面是大神的部落格 以下是自己的總結 可能不定期更新 下面是gradle依賴的包 compil...

簡述hdfs工作原理 HDFS的工作原理

hdfs 的工作原理 hadoop 分布式檔案系統 hdfs 是一種被設計成適合執行在通用硬體上的分布式檔案系統。hdfs 是乙個高度容錯性的系統,適合部署在廉價的 機器上。它能提供高吞吐量的資料訪問,非常適合大規模資料集上的應用。要理解 hdfs 的內部工作原理,首先要理解什麼是分布式 檔案系統。...

mysql nfs原理 nfs工作原理

nfs其最大功能時可以通過網路讓不同作業系統的計算機可以共享資料,所以也可以將其看作時一台檔案伺服器.nfs有屬於自己的協議與使用的埠號,但是在傳送資料或者其他相關資訊時候,nfs伺服器使用乙個稱i 遠端過程呼叫 rpc 的協議來協助nfs伺服器本身的執行 nfs協議 使用nfs,客戶端可以透明地訪...