lucene4.7 鎖機制(十)

Lucene的索引體系是一個寫獨佔,讀共享的結構,這意味着,咱們在使用多線程進行添加索引時,性能並不會獲得明顯的提高,因此任什麼時候刻只能有一個線程對索引進行寫入操做,而保障這個操做的安全性則是來自於,Lucene獨特的鎖機制(寫入操做進行時,咱們能夠在Lucene的索引根目錄裏看到一個命名爲write.lock的鎖文件),若是同一時刻有多個不一樣IndexWriter對索引進行寫入操做,那麼將會引起鎖重疊異常,因此Lucene的特殊的索引結構,決定了其只能使用一個IndexWriter對索引進行添加操做。 

即便是限定Lucen只能使用一個線程進行寫入操做,Lucene的寫入性能也是很是高效的,特別是在Lucene4.x以後,更是優異,咱們能夠根據本身服務器的硬件環境,來調優一些參數,利用上批處理的特性,能夠大大提高寫入性能。 

前面說過,Lucene寫入時只能用一個線程操做,那麼假如咱們想使用多線程寫入來提速能夠嗎? 
答案是確定的,雖然Lucene限定只能用一個線程寫入,可是這個限制僅僅指的是對一個索引文件的限制,咱們能夠採起一種折中的方式,利用多個線程寫入多個索引文件夾目錄,最後在對這幾個索引文件合併,由此來提高索引速度,Lucene的API也支持多個索引文件的合併,因此採用這種方式來建索引,也可以大大的提高索引性能,這種方式尤爲適用於對數據庫的數據建索引,咱們能夠採用分頁讀的方式,由某個固定數目的線程來建索引。 

本篇就來介紹下,如何使用LuceneD的API 來對多個索引文件進行合併操做,合併操做大多數時候要求咱們的數據結構是要一致的,固然Lucene是一種文檔型的鬆散的存儲結構,某個文檔裏也能夠存儲本身特有的字段,而其餘的文檔裏,則沒有,不過既然是咱們須要合併,那麼就要求大多數的結構是要一致的,不然兩個徹底不一樣類型的索引,合併到一塊兒也是不符合邏輯的。 


爲了演示合併,就創建了2份索引,而後對這兩份索引進行合併。截圖以下:java

合併的核心代碼以下:
web

/***
     * @author 秦東亮
     * lucene 技術交流羣:324714439
     * 測試多個索引之間
     * 進行合併的方法
     * **/
      public static void combineMoreIndex(){
          
          try{
          Directory d1=FSDirectory.open(new File("E:\\1\\a"));//打開存放索引1的路徑
          Directory d2=FSDirectory.open(new File("E:\\2\\a"));//打開存放索引2的路徑
          
          Directory d3=FSDirectory.open(new File("E:\\3\\ab"));//合併到索引3裏面
          
           IndexWriter writer=new IndexWriter(d3, new IndexWriterConfig(Version.LUCENE_44, new IKAnalyzer()));
          
           writer.addIndexes(d1,d2);//傳入各自的Diretory或者IndexReader進行合併
           writer.commit();//提交索引
           writer.close();
           System.out.println("合併索引完畢.........");
          
          
          }catch(Exception e){
              e.printStackTrace();
          }
      }

生成的第三份索引,截圖以下:
數據庫

下面咱們來看下,合併前,1,2索引和合並後的3索引的數據變化信息。
安全

  System.out.println("==============1a=========================");
           showAll("E:\\1\\a");
           System.out.println("==============2a=========================");
           showAll("E:\\2\\a");
           System.out.println("==============合併後=========================");
           showAll("E:\\3\\ab");

輸出結果以下,注意裏面有日期爲null的,表明這個文檔沒有日期的這個字段。
服務器

==============1a=========================
a===>中國  日期: ===> null
b===>法國  日期: ===> 1389783935597
c===>中國  日期: ===> null
d===>英國  日期: ===> null
==============2a=========================
q===>中國  日期: ===> null
w===>法國  日期: ===> 1389783980586
r===>中國  日期: ===> null
d===>英國  日期: ===> null
==============合併後=========================
a===>中國  日期: ===> null
b===>法國  日期: ===> 1389783935597
c===>中國  日期: ===> null
d===>英國  日期: ===> null
q===>中國  日期: ===> null
w===>法國  日期: ===> 1389783980586
r===>中國  日期: ===> null
d===>英國  日期: ===> null
相關文章
相關標籤/搜索