相信很多人都有過HTML文檔解析的需求。比如我們抓取了某1個網站的頁面資料,格式就是HTML的格式。以前我們都是通過正規表達式來進行解析,但是發現有一些問題。解析HTML文檔時并不容易,如果文檔的格式稍有變化很可能就不能正确的比對。是以我們需要專門的工具來幫助我們輕松的解析HTML文檔。
其實已經有一個非常不錯的工具提供了。比如HtmlAgilityPack。它可以幫助我們解析HTML文檔就像用XmlDocument類來解析XML一樣輕松、友善。
好了,下面提供一個足夠Simple的例子給大家。大家可以在此基礎之上,舉一反三。
比如要解析下面的HTML。
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
<code><</code><code>table</code><code>></code>
<code> </code><code><</code><code>thead</code><code>></code>
<code> </code><code><</code><code>tr</code><code>></code>
<code> </code><code><</code><code>th</code><code>>時間</</code><code>th</code><code>></code>
<code> </code><code><</code><code>th</code><code>>類型</</code><code>th</code><code>></code>
<code> </code><code><</code><code>th</code><code>>名稱</</code><code>th</code><code>></code>
<code> </code><code><</code><code>th</code><code>>機關</</code><code>th</code><code>></code>
<code> </code><code><</code><code>th</code><code>>金額</</code><code>th</code><code>></code>
<code> </code><code></</code><code>tr</code><code>></code>
<code> </code><code></</code><code>thead</code><code>></code>
<code> </code><code><</code><code>tbody</code><code>></code>
<code> </code><code><</code><code>td</code><code>>2013-12-29</</code><code>td</code><code>></code>
<code> </code><code><</code><code>td</code><code>>發票1</</code><code>td</code><code>></code>
<code> </code><code><</code><code>td</code><code>>采購物資發票1</</code><code>td</code><code>></code>
<code> </code><code><</code><code>td</code><code>>某某公司1</</code><code>td</code><code>></code>
<code> </code><code><</code><code>td</code><code>>123元</</code><code>td</code><code>></code>
<code> </code><code><</code><code>td</code><code>>發票2</</code><code>td</code><code>></code>
<code> </code><code><</code><code>td</code><code>>采購物資發票2</</code><code>td</code><code>></code>
<code> </code><code><</code><code>td</code><code>>某某公司2</</code><code>td</code><code>></code>
<code> </code><code><</code><code>td</code><code>>321元</</code><code>td</code><code>></code>
<code></</code><code>table</code><code>></code>
以控制台項目為例,首先要引用HtmlAgilityPack.dll檔案,這樣才能使用dll裡面的類和方法。
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
<code>static</code> <code>void</code> <code>Main(</code><code>string</code><code>[] args)</code>
<code>{</code>
<code> </code><code>string</code> <code>strWebContent = </code><code>@"<table><thead></code>
<code> </code><code><tr></code>
<code> </code><code><th>時間</th></code>
<code> </code><code><th>類型</th></code>
<code> </code><code><th>名稱</th></code>
<code> </code><code><th>機關</th></code>
<code> </code><code><th>金額</th></code>
<code> </code><code></tr></code>
<code> </code><code></thead></code>
<code> </code><code><tbody>"</code> <code>+</code>
<code> </code><code>@"<tr></code>
<code> </code><code><td>2013-12-29</td></code>
<code> </code><code><td>發票1</td></code>
<code> </code><code><td>采購物資發票1</td></code>
<code> </code><code><td>某某公司1</td></code>
<code> </code><code><td>123元</td></code>
<code> </code><code></tr>"</code> <code>+</code>
<code> </code><code><td>發票2</td></code>
<code> </code><code><td>采購物資發票2</td></code>
<code> </code><code><td>某某公司2</td></code>
<code> </code><code><td>321元</td></code>
<code> </code><code></tbody></code>
<code> </code><code></table></code>
<code>"</code><code>;</code>
<code> </code>
<code> </code><code>List<Data> datas = </code><code>new</code> <code>List<Data>();</code><code>//定義1個清單用于儲存結果</code>
<code> </code><code>HtmlDocument htmlDocument = </code><code>new</code> <code>HtmlDocument();</code>
<code> </code><code>htmlDocument.LoadHtml(strWebContent);</code><code>//加載HTML字元串,如果是檔案可以用htmlDocument.Load方法加載</code>
<code> </code><code>HtmlNodeCollection collection = htmlDocument.DocumentNode.SelectSingleNode(</code><code>"table/tbody"</code><code>).ChildNodes;</code><code>//跟Xpath一樣,輕松的定位到相應節點下</code>
<code> </code><code>foreach</code> <code>(HtmlNode node </code><code>in</code> <code>collection)</code>
<code> </code><code>{</code>
<code> </code><code>//去除\r\n以及空格,擷取到相應td裡面的資料</code>
<code> </code><code>string</code><code>[] line = node.InnerText.Split(</code><code>new</code> <code>char</code><code>[] { </code><code>'\r'</code><code>, </code><code>'\n'</code><code>, </code><code>' '</code> <code>}, StringSplitOptions.RemoveEmptyEntries);</code>
<code> </code><code>//如果符合條件,就加載到對象清單裡面</code>
<code> </code><code>if</code> <code>(line.Length == 5)</code>
<code> </code><code>datas.Add(</code><code>new</code> <code>Data() { 時間 = line[0], 類型 = line[1], 名稱 = line[2], 機關 = line[3], 金額 = line[4] });</code>
<code> </code><code>}</code>
<code> </code><code>//循環輸出檢視結果是否正确</code>
<code> </code><code>foreach</code> <code>(</code><code>var</code> <code>v </code><code>in</code> <code>datas)</code>
<code> </code><code>Console.WriteLine(</code><code>string</code><code>.Join(</code><code>","</code><code>, v.時間, v.類型, v.名稱, v.機關, v.金額));</code>
<code>}</code>
<code>/// <summary></code>
<code>/// 定義的實體類用于接收資料</code>
<code>/// </summary></code>
<code>public</code> <code>class</code> <code>Data</code>
<code> </code><code>public</code> <code>string</code> <code>時間 { </code><code>get</code><code>; </code><code>set</code><code>; }</code>
<code> </code><code>public</code> <code>string</code> <code>類型 { </code><code>get</code><code>; </code><code>set</code><code>; }</code>
<code> </code><code>public</code> <code>string</code> <code>名稱 { </code><code>get</code><code>; </code><code>set</code><code>; }</code>
<code> </code><code>public</code> <code>string</code> <code>機關 { </code><code>get</code><code>; </code><code>set</code><code>; }</code>
<code> </code><code>public</code> <code>string</code> <code>金額 { </code><code>get</code><code>; </code><code>set</code><code>; }</code>
上面就是完整的代碼,注釋也很清楚。
最後看一下解析的結果:

本文轉自 guwei4037 51CTO部落格,原文連結:http://blog.51cto.com/csharper/1346611