2012-10-04

[C#]Lucene.net–合併索引


這一篇來說一下一個我覺得也會常用到的合併索引..

資料概述

在  CIndex1 中有已存在資料索引 1~1200
其搜尋'當麻'關鍵字結果為
2012-10-04_163420_thumb[1]
在資料夾 CIndex2 中有已存在資料索引 11001~12000
其搜尋'當麻'關鍵字結果為
2012-10-04_163426_thumb[1]

這時候我們進行合併Index

//來源的兩個index路徑



FSDirectory indexDir1 =  FSDirectory.Open(new DirectoryInfo(AppDomain.CurrentDomain.BaseDirectory + "\\CIndex1\\"));

FSDirectory indexDir2 = FSDirectory.Open(new DirectoryInfo(AppDomain.CurrentDomain.BaseDirectory + "\\CIndex2\\"));

FSDirectory indexDir3 = FSDirectory.Open(new DirectoryInfo(AppDomain.CurrentDomain.BaseDirectory + "\\CIndex3\\"));



IndexWriter indexWriter = new IndexWriter(indexDir3, new StandardAnalyzer(Lucene.Net.Util.Version.LUCENE_29), true, IndexWriter.MaxFieldLength.UNLIMITED);



//indexWriter.SetMergeFactor(100000);

//indexWriter.SetMaxFieldLength(int.MaxValue);

//indexWriter.SetMaxBufferedDocs(int.MaxValue);





indexWriter.AddIndexesNoOptimize( new Lucene.Net.Store.Directory[] { indexDir1, indexDir2  });

indexWriter.Optimize();

indexWriter.Close();



程式碼中我把CIndex1 和 CIndex2  的索引合併後放置在CIndex3 中

其中註解的部份

SetMergeFactor 是控制 segment 合併頻率的,決定了一個索引segment 中包括多少個文檔,當硬碟上的索引segment 達到多少時,將它們合併成一個較大的索引塊。當 MergeFactor 值較大時,生成索引的速度較快。MergeFactor 的默認值是 10,建議在建立索引前將其設置的大一些。

SetMaxBufferedDocs 是控制寫入一個新的 segment 前內存中保存的 document 的數目,設置較大的數目可以加快建索引速度,預設為 10。

這時候我們對 CIndex3 的資料進行關鍵字搜尋..

// 啟用監看
Stopwatch sw = new Stopwatch();
sw.Start();

// 讀取索引
string indexPath = AppDomain.CurrentDomain.BaseDirectory.ToString() + "\\CIndex3\\";
DirectoryInfo dirInfo = new DirectoryInfo(indexPath);
FSDirectory dir = FSDirectory.Open(dirInfo);
IndexSearcher search = new IndexSearcher(dir, true);
// 針對 Memo 欄位進行搜尋
QueryParser parser = new QueryParser(Lucene.Net.Util.Version.LUCENE_29, "Memo", new StandardAnalyzer(Lucene.Net.Util.Version.LUCENE_29));
// 搜尋的關鍵字
Query query = parser.Parse(txtKeyword.Text);
// 開始搜尋
var hits = search.Search(query, null, search.MaxDoc()).ScoreDocs;

sw.Stop();
Response.Write("花費時間:" + sw.Elapsed + "<br /><hr />");
Response.Write("資料比數:" + hits.Length + "<br /><hr />");
Response.Write("Result:<br />");

foreach (var res in hits)
{
 //支援Lucene.net 3.0 的做法
 Response.Write("Id:" + search.Doc(res.doc).Get("Id") + "  BirthDay=" + search.Doc(res.doc).Get("BirthDay") + "  Memo=" + search.Doc(res.doc).Get("Memo").ToString().Replace(txtKeyword.Text, "<span style='color:red'>" + txtKeyword.Text + "</span>") + "<br />");
}

//以前的寫法
//for (int i = 0; i < hits.Length; i++)
//{

//    Response.Write("Id:" + search.Doc(i).Get("Id").ToString() + "  Memo=" + search.Doc(i).Get("Memo").ToString().Replace(txtKeyword.Text, "<span style='color:red'>" + txtKeyword.Text + "</span>") + "<br />");
//}

結果:

2012-10-04_163509_thumb[1]



參考: http://www.kuqin.com/searchengine/20081110/26415.html