HtmlAgilityPack和大型HTML文档

时间:2012-10-09 16:20:02

标签: c# httpwebrequest html-agility-pack

我已经构建了一个小爬虫,现在在尝试时我发现在抓取某些网站时,我的抓取工具使用98-99%的CPU。

我使用dotTrace来查看问题可能是什么,它指向我的httpwebrequest方法 - 我在stackoverflow上的一些先前的问题的帮助下优化了一点..但问题还在那里。

然后我去了解导致CPU负载的URL,发现它实际上是非常大的网站 - 去图:) 所以,现在我99%肯定它与下面的代码有关:

HtmlAgilityPack.HtmlDocument documentt = new HtmlAgilityPack.HtmlDocument();
HtmlAgilityPack.HtmlNodeCollection list;
HtmlAgilityPack.HtmlNodeCollection frameList;

documentt.LoadHtml(_html);
list = documentt.DocumentNode.SelectNodes(".//a[@href]");

我想要做的就是提取页面上的链接,所以对于大型网站..无论如何我可以得到这个不使用这么多的CPU?

我在考虑限制我取的东西?什么是我最好的选择?

当然,有人必须在遇到此问题之前:)

3 个答案:

答案 0 :(得分:1)

“。// [@href]”是非常慢的XPath。试图用“// a [@href]”或代码简单地遍历整个文档并检查所有A节点。

为什么这个XPath很慢:

  1. “”。从节点开始
  2. “//”选择所有后代节点
  3. “a” - 仅选择“a”节点<​​/ li>
  4. “@ href”with href。
  5. 部分1 + 2以“为每个节点选择所有其后代节点”结束,这非常慢。

答案 1 :(得分:1)

您是否尝试过删除XPath并使用LINQ功能?

var list = documentt.DocumentNode.Descendants("a").Select(n => n.GetAttributeValue("href", string.Empty);

这会将所有锚标记的href属性列表拉为List&lt; string&gt;。

答案 2 :(得分:1)

如果您没有大量投资Html Agility Pack,请尝试使用CsQuery。它在解析文档时构建索引,而选择器比HTML Agility Pack快得多。见a comparison.

CsQuery是一个带有完整CSS选择器引擎的.NET jQuery端口;它允许您使用CSS选择器以及jQuery API来访问和操作HTML。它是作为CsQuery的nuget。