HTML 敏捷包:解析 href 标签
Posted
技术标签:
【中文标题】HTML 敏捷包:解析 href 标签【英文标题】:HTML Agility pack: parsing an href tag 【发布时间】:2012-01-19 19:49:00 【问题描述】:我将如何有效地从中解析 href 属性值:
<tr>
<td rowspan="1" colspan="1">7</td>
<td rowspan="1" colspan="1">
<a class="undMe" href="/ice/player.htm?id=8475179" rel="skaterLinkData" shape="rect">D. Kulikov</a>
</td>
<td rowspan="1" colspan="1">D</td>
<td rowspan="1" colspan="1">0</td>
<td rowspan="1" colspan="1">0</td>
<td rowspan="1" colspan="1">0</td>
[...]
我有兴趣拥有玩家 ID,即:8475179这是我目前拥有的代码:
// Iterate all rows (players)
for (int i = 1; i < rows.Count; ++i)
htmlNodeCollection cols = rows[i].SelectNodes(".//td");
// new player
Dim_Player player = new Dim_Player();
// Iterate all columns in this row
for (int j = 1; j < 6; ++j)
switch (j)
case 1: player.Name = cols[j].InnerText;
player.Player_id = Int32.Parse(/* this is where I want to parse the href value */);
break;
case 2: player.Position = cols[j].InnerText; break;
case 3: stats.Goals = Int32.Parse(cols[j].InnerText); break;
case 4: stats.Assists = Int32.Parse(cols[j].InnerText); break;
case 5: stats.Points = Int32.Parse(cols[j].InnerText); break;
【问题讨论】:
如果switch
中有硬编码索引,为什么要使用for
循环?为什么不player.Position = cols[2].InnerText;
好点。我正在回收我写的一些旧代码,所以我没有想到。
【参考方案1】:
使用 XPath 表达式查找它:
foreach (HtmlNode link in doc.DocumentNode.SelectNodes("//a[@class='undMe']"))
HtmlAttribute att = link.Attributes["href"];
Console.WriteLine(new Regex(@"(?<=[\?&]id=)\d+(?=\&|\#|$)").Match(att.Value).Value);
【讨论】:
【参考方案2】:根据您的示例,这对我有用:
HtmlDocument htmlDoc = new HtmlDocument();
htmlDoc.Load("test.html");
var link = htmlDoc.DocumentNode
.Descendants("a")
.First(x => x.Attributes["class"] != null
&& x.Attributes["class"].Value == "undMe");
string hrefValue = link.Attributes["href"].Value;
long playerId = Convert.ToInt64(hrefValue.Split('=')[1]);
实际使用需要添加错误检查等
【讨论】:
对我也有用!只是我还是这很不方便,因为我们必须使用htmlDoc
,在其中我们可以找到所有具有“undMe”类的节点,而我们可以使用cols[j]
,它的InnerHtml 中有href
?
您对链接的位置做出了非常强烈的假设 - 这可能工作正常,但非常僵化并且会中断,即如果您添加另一列。所提出的方法不会因为它在最小假设下查询链接
实际上,唯一的问题是First()
,它是静态的,总是带来他找到的第一个元素。我需要一些动态的东西来获取实际元素。
啊……找到了:var link = cols.Descendants("a").First();
,因为我只想在我已经找到的列中搜索。
这是一个很棒的答案......它工作得很好。唯一的问题是将 .First 替换为 .FirstOrDefault ,否则会抛出异常。以上是关于HTML 敏捷包:解析 href 标签的主要内容,如果未能解决你的问题,请参考以下文章