如何使用敏捷包从 HTML 文档访问当前节点和后代?

How to access current node and descendants from HTML document with agility package?

我将 HTML 加载到 HTML 文档 中。现在我想 access/select 每个 dt 与属于 dt 的每个 dd 和将其存储在数组中以备后用。我已经尝试过 http://www.w3schools.com/xsl/xpath_axes.asp 中提到的 XPath 语法,但它根本不起作用。我刚收到 NullReferenceException。但是我做错了什么?

请记住,有时一个 **dt** 有 2 个或更多 **dd** 个元素。我想将每个 **dd** 元素添加到相应的 **dt**.

非常感谢。

<dl>
  <dt id="one">one</dt>
  <dd>some text</dd>
  <dt id="two">two</dt>
  <dd>some text</dd>
  <dt id="three">three</dt>
  <dd>some text</dd>
  <dd>some text</dd>
  <dt id="four">four</dt>
  <dd>some text</dd>
  and so on...
</dl>

dtdd 元素之间没有直接的 link,这就是为什么我个人没有找到使用 XPath 为您提供解决方案的原因。 XSLT 可能是一个选项,但是,我也没有找到使用 XSLT 的快捷方式。 由于您使用 C#,我制作了一个快速原型函数,说明它在 C# 中的外观:

public static void Main(string[] args)
        {            
            Dictionary<string, List<string>> dt = new Dictionary<string, List<string>>();        

            using(XmlReader reader = XmlReader.Create(@"data.xml")){
                bool incomingDd = false;
                while(reader.Read()){
                    switch(reader.NodeType){
                        case XmlNodeType.Element:                            
                            if(String.Equals(reader.Name, "dt", StringComparison.OrdinalIgnoreCase)){
                                dt.Add(reader.GetAttribute("id"), new List<string>());
                            }
                            else if(String.Equals(reader.Name, "dd", StringComparison.OrdinalIgnoreCase)){
                                incomingDd = true;                                
                            }
                            break;

                        case XmlNodeType.Text:                                
                            if(incomingDd && !String.IsNullOrEmpty(reader.Value)){                                
                                dt.Values.ElementAt(dt.Count -1).Add(reader.Value);
                                incomingDd = false;
                            }
                            break;
                    }
                }
            }

            foreach(var item in dt){
                Console.WriteLine($"{item.Key} {item.Value.Count()}:");
                foreach(var dd in item.Value){
                    System.Console.WriteLine($"\t{dd}");
                }
            }
        }

这可能不是满足您需求的最漂亮的代码,但应该能让您了解如何解决您的问题。