Html Agility Packを使ってXPathでWebページをスクレイピングする

NuGetでHtml Agility Packを追加。

例(VB.NETコード)

Sub Main()
  Console.WriteLine("HttpClientクラスで取得したWebページを解析する(Html Agility Pack)")
  ' 時間計測用のタイマー
  Dim timer = New System.Diagnostics.Stopwatch()
  timer.Start()

  ' .NET TIPSの日付順インデックスのURL(シフトJISのページ)
  Dim webUri As Uri = New Uri("http://www.atmarkit.co.jp/ait/subtop/features/dotnet/index_date.html")
  ……省略……
  Dim htmlText As String = ……省略(Webページの内容を文字列として取得)……
  Console.WriteLine("HTML取得完了: {0:0.000}秒", timer.Elapsed.TotalSeconds)

  If (htmlText IsNot Nothing) Then
    ' HtmlDocumentオブジェクトを構築する
    Dim htmlDoc = New HtmlAgilityPack.HtmlDocument()
    htmlDoc.LoadHtml(htmlText)
    Console.WriteLine("HtmlDocument構築完了: {0:0.000}秒", timer.Elapsed.TotalSeconds)

    ' 目的の<a>要素を全て取り出して(XPath)、
    ' そのhref属性とInnerTextを持つ匿名型オブジェクトのコレクションを作る(LINQ)
    Dim articles _
      = htmlDoc.DocumentNode _
        .SelectNodes("//div[@class=""da-tips-index-target""]/div[not(@class)]/a") _
        .Select(Function(a) New With _
                            {
                              .Url = a.Attributes("href").Value.Trim(),
                              .Title = a.InnerText.Trim()
                            })
    Console.WriteLine("タイトル取り出し完了: {0:0.000}秒", timer.Elapsed.TotalSeconds)
    Console.WriteLine()

    ' 先頭10件を表示する
    Console.WriteLine("記事タイトル先頭10件(全{0}記事中)", articles.Count())
    For Each a In articles.Take(10)
      Console.WriteLine(a.Title)
      Console.WriteLine(" - {0}", a.Url)
    Next
  End If
#If DEBUG Then
  Console.ReadKey()
#End If
End Sub