2016-12-07 12 views
0

私は、示すが、私はいくつかの問題HTMLAgilityPackを使用してHTMLデータを解析する

public class Book 
    { 
     public HtmlAttribute Href{ get; set; } 
     public string Title{ get; set; } 
     public string Author{ get; set; } 
     public string Characters{ get; set; } 
    } 

これは私が解析しようとしているページですを得ただろう、私は、リンク、時々説明文字リストhrefの値を必要としますそこに何も)ではありません:

<div id=title> 
     <li> 
      <h3><a href="www.harrypotter.com">Harry Potter</a></h3> 
      <div>Harry James Potter is the title character of J. K. Rowling's Harry Potter series. </div> 
      <ul> 
       <li>Harry Potter</li> 
       <li>Hermione Granger</li> 
       <li>Ron Weasley</li> 
      </ul> 
     </li> 

     <li> 
      <h3><a href="www.littleprince.com">Little Prince</a></h3> 
      <div>A little girl lives in a very grown-up world with her mother, who tries to prepare her for it. </div> 
     </li> 
    </div> 

そして、これはそれを解析して、リストにそれを置くために私のコードです

List<Book> BookList= new List<Book>(); 
    var titleNode = doc.DocumentNode.SelectNodes("//*[@id=\"title\"]//li//h3"); 
    var descNode = doc.DocumentNode.SelectNodes("//*[@id=\"title\"]//li//div"); 
    var authorNode = doc.DocumentNode.SelectNodes("//*[@id=\"title\"]//li//ul"); 

    var title = titleNode.Select(node => node.InnerText).ToList(); 
    var desc = descNode.Select(node => node.InnerText).ToList(); 
    var characters= authorNode.Select(node => node.InnerText).ToList(); 

    for (int i = 0; i < Title.Count(); ++i) 
    { 
     var list= new Book(); 
     list.Title= title[i]; 
     list.Author= desc[i]; 
     list.Characters = characters[i]; 
     BookList.Add(list); 
    } 

私の質問は次のとおりです。1)href値を取得してリストに追加するにはどうすればよいですか? 2)HTMLの中に文字のタグがないものもありますが、NullReferenceExceptionエラーが発生してもリストを取得するにはどうすればよいですか?注:私はhtmlを変更することはできません。

答えて

0

私はHTMLAgilityPackを使用せずに、あなたの問題を解決する必要があり、ここで私がSystem.Xmlの

注意を使用しています:あなたはいくつかのユニークな値を追加する必要があり、メイン要素を識別するために、ここで私は、「メイン」としてクラスを追加しました

using System; 
using System.Collections.Generic; 
using System.Linq; 
using System.Text; 
using System.Xml; 

namespace Test 
{ 
public class Book 
{ 
    public string Href { get; set; } 
    public string Title { get; set; } 
    public string Author { get; set; } 
    public string Characters { get; set; } 
} 

class Program 
{ 
    static void Main(string[] args) 
    { 
     string str="<div id='title'><li class='Main'><h3><a href='www.harrypotter.com'>Harry Potter</a></h3><div>Harry James Potter is the title character of J. K. Rowling's Harry Potter series. </div>"; 
     str += "<ul><li>Harry Potter</li><li>Hermione Granger</li><li>Ron Weasley</li></ul></li><li class='Main'><h3><a href='www.littleprince.com'>Little Prince</a></h3><div>A little girl lives in a very grown-up world with her mother, who tries to prepare her for it. </div></li></div>"; 

     XmlDocument doc = new XmlDocument(); 
     doc.LoadXml(str); 

     XmlNodeList xnList= doc.SelectNodes("//*[@id=\"title\"]//li[@class=\"Main\"]"); 

     List<Book> BookList=new List<Book>(); 

     for (int i = 0; i < xnList.Count; i++) 
     { 
      XmlNode TitleNode = xnList[i].SelectSingleNode("h3"); 
      XmlNode DescNode = xnList[i].SelectSingleNode("div"); 
      XmlNode AuthorNode = xnList[i].SelectSingleNode("ul"); 

      Book list = new Book(); 
      if(TitleNode!=null) 
       list.Title=TitleNode.InnerText; 
      else 
       list.Title=""; 

      if (DescNode != null) 
       list.Author = DescNode.InnerText; 
      else 
       list.Author = string.Empty; 

      if (AuthorNode != null) 
       list.Characters = AuthorNode.InnerText; 
      else 
       list.Characters = string.Empty; 

      if (TitleNode != null && TitleNode.ChildNodes.Count>0) 
      { 
       XmlNode HrefNode = TitleNode.ChildNodes[0]; 
       if (HrefNode != null && HrefNode.Attributes.Count > 0 && HrefNode.Attributes["href"] != null) 
        list.Href = HrefNode.Attributes["href"].Value; 
       else 
        list.Href = string.Empty; 
      } 
      else 
      { 
       list.Href = string.Empty; 
      } 

      BookList.Add(list); 
     } 
    } 
} 
} 
+0

私が解析しようとしているウェブサイトからのものであるため、htmlを変更できません。 – Blake

0

これは私がやる方法です。あなたの質問を教えてあげてください。

 //get all li(s) 
     var lis = doc.DocumentNode.Descendants("li").Where(_ => _.ParentNode.Id.Equals("title")); 
     foreach (var li in lis) 
     { 
      //get tile and href 
      var title = li.Descendants("h3").FirstOrDefault().InnerText; //you can check null or empty here 
      var href = li.Descendants("h3").FirstOrDefault(_ => _.Name.Equals("a"))?.Attributes["href"]; //again check null here 
      var desc = li.Descendants("div").FirstOrDefault().InnerHtml; 
      var characters = li.Descendants("ul").FirstOrDefault()?.Descendants("li"); 
      foreach (var character in characters) 
      { 
       var val = character.InnerText; 
      } 
     } 
関連する問題