如何在C# HtmlAgilityPack同一循环中获取标签文本与属性值
解决HtmlAgilityPack遍历TR行时获取INPUT属性的问题
问题场景
处理的HTML结构如下:
</TR> <TR> <TD ALIGN="center"> <INPUT TYPE="checkbox" NAME="f0" VALUE="14652 4-76-17-7-2024-R" ONCLICK=uncheck("f0")> </TD> <TD> </TD> <TD>76/07-17</TD> <TD>14652</TD> <TD> </TD> <TD>9.3</TD> <TD> 78 </TD> <TD> </TD> <TD> </TH> </TR>
当前用HtmlAgilityPack循环获取TR下的TD文本时,无法同时获取行内INPUT标签的Name和Value属性值,导致数据不完整。原有代码中row.SelectSingleNode("//td//input")会始终返回整个文档中第一个INPUT,无法遍历每行的对应元素,还会出现空引用异常。需求是将TD文本与INPUT的Name、Value整合到同一行数据中。
解决方案
核心修改点:
- 使用相对XPath路径(
.//td//input)替代绝对路径,确保只查找当前TR行下的INPUT元素 - 增加空引用判断,避免无INPUT的行抛出异常
- 将INPUT的Name和Value属性值追加到当前行的数据数组中
修改后的代码:
HtmlAgilityPack.HtmlDocument doc = new HtmlAgilityPack.HtmlDocument(); doc.LoadHtml(page); foreach (var row in doc.DocumentNode.SelectNodes("//tr[td]")) { // 获取当前行所有TD的文本内容(Trim去除多余空格) var tdTexts = row.SelectNodes("td").Select(td => td.InnerText.Trim()).ToList(); // 查找当前行内的INPUT元素(相对路径,仅在当前row节点下搜索) var inputNode = row.SelectSingleNode(".//td//input"); if (inputNode != null) { // 安全获取属性值:属性不存在时返回空字符串 string inputName = inputNode.GetAttributeValue("name", string.Empty); string inputValue = inputNode.GetAttributeValue("value", string.Empty); // 将属性值追加到行数据末尾 tdTexts.Add(inputName); tdTexts.Add(inputValue); } else { // 无INPUT时追加空值,保证所有行的列数一致 tdTexts.Add(string.Empty); tdTexts.Add(string.Empty); } // 把整合后的数据添加到表格 table.Rows.Add(tdTexts.ToArray()); }
关键说明
- 相对XPath:
.//td//input中的.表示从当前TR节点开始查找,彻底解决了全局匹配第一个INPUT的问题。 - GetAttributeValue方法:相比直接访问
Attributes["name"].Value,该方法内置空值处理,避免属性不存在时抛出空引用异常。 - 列数一致性:无INPUT的行也追加两个空值,确保表格所有行的列数统一,不会破坏表格结构。
内容的提问来源于stack exchange,提问作者Fazlan Fawmy
相关产品推荐
相关产品推荐

