2012-01-30 48 views
0

我有一個應用程序,它可以爬網並將內容作爲lucene索引文件寫入物理目錄。線程安全寫入Lucene索引文件

當我使用線程來達到這個目的時,我得到了寫入錯誤或由於鎖定而導致的錯誤。

我想使用多個線程並寫入索引文件而不會錯過任何線程的任務。如果我添加t.Join();t.Start();後的代碼工作對我來說沒有任何錯誤

DocumentSettings writedoc = new DocumentSettings() 
{ 
     Host = Host, 
     downloadedDocument = downloadDocument 
}; 
Thread t = new Thread(() => 
{ 
doc.AddDocument(writedoc); 
}); 
t.Start(); 

public class WriteDocument 
{ 
    private static Analyzer _analyzer; 

    private static IndexWriter indexWriter; 

    private static string Host; 

    public WriteDocument(string _Host) 
    { 
     Host = _Host; 
     Lucene.Net.Store.Directory _directory = FSDirectory.GetDirectory(Host, false); 
     _analyzer = new StandardAnalyzer(); 
     bool indexExists = IndexReader.IndexExists(_directory); 
     bool createIndex = !indexExists; 

     indexWriter = new IndexWriter(_directory, _analyzer, true); 
    } 
    public void AddDocument(object obj) 
    { 
      DocumentSettings doc = (DocumentSettings)obj;    
      Field urlField = new Field("Url", doc.downloadedDocument.Uri.ToString(), Field.Store.YES, Field.Index.TOKENIZED); 
      document.Add(urlField); 
      indexWriter.AddDocument(document); 

      document = null; 
      doc.downloadedDocument = null; 

      indexWriter.Optimize(); 
      indexWriter.Close(); 
     } 
} 

爲了上面的類,我傳遞的價值觀是這樣的。但是這會減慢我的過程,實際上,這等於不使用線程的輸出。

我收到錯誤,如:

Cannot rename /indexes/Segments.new to /indexes/Segments 
the file is used by some other process. 

任何人都可以幫助我在此代碼?

+0

你會得到什麼錯誤?我們可以看到您正在使用的代碼的一個小例子嗎? – unholysampler 2012-01-30 11:52:09

+0

添加了清晰的代碼 – 2012-01-30 12:31:47

回答

0

IndexWriter不是線程安全的,所以這是不可能的。

如果您想要使用多個線程進行下載,您需要構建某種單線程的「消息泵」,您可以將正在下載和創建的文檔提供給它,並將它們放入隊列中。

例如,在您的AddDocument方法中,不是直接使用索引,而是將它們發送到最終將索引它的服務。

該服務應該嘗試索引隊列中的所有內容,如果它暫時沒有隊列,請稍等片刻。

+0

好吧,我很困惑 - Lucene.net 3.0.3文檔說IndexWriter是[線程安全的](https://lucenenet.apache.org/docs/3.0.3/d2/d1d/ class_lucene_1_1_net_1_1_index_1_1_index_writer.html#細節) – chester89 2016-04-14 06:47:49

0

您可以採取的方法是爲每個線程創建一個單獨的索引,並將它們全部合併回去。例如index1,index2 ... indexn(對應於線程1..n)併合並它們。