通过 PHP 从网站中提取数据
Posted
技术标签:
【中文标题】通过 PHP 从网站中提取数据【英文标题】:Extract data from website via PHP 【发布时间】:2011-01-02 10:57:37 【问题描述】:我正在尝试为一些朋友创建一个简单的警报应用程序。
基本上我希望能够从如下两个网页中提取数据“价格”和“库存可用性”:
http://www.sparkfun.com/commerce/product_info.php?products_id=5 http://www.sparkfun.com/commerce/product_info.php?products_id=9279我已通过电子邮件和短信部分发出警报,但现在我希望能够从网页(这 2 个或任何其他网页)中获取数量和价格,以便我可以比较可用的价格和数量如果产品在某些阈值之间,并提醒我们下订单。
我已经尝试了一些正则表达式(在一些教程中找到,但我对此太过分了)但还没有设法让它工作,有什么好的提示或例子吗?
【问题讨论】:
你可以发布你迄今为止尝试过的内容...... 不要使用正则表达式解析 html。您无法使用正则表达式可靠地解析 HTML,并且您将面临悲伤和挫败感。一旦 HTML 与您的期望发生变化,您的代码就会被破坏。有关如何使用已经编写、测试和调试的 PHP 模块正确解析 HTML 的示例,请参阅 htmlparsing.com/php。 【参考方案1】:无论做什么:不要使用正则表达式来解析 HTML 或 bad things will happen。请改用parser。
【讨论】:
我认为正则表达式适用于非常具体的用例(即标记/文本始终相同)。但当然不是用于验证 HTML 等。解析器始终是一个很好的解决方案,但有时它们是矫枉过正的。 我认为正则表达式可以解决问题,因为我只尝试从页面中提取 2 个信息,而且格式非常标准...... @Felix 您是否阅读了有关尝试使用正则表达式解析 HTML 时会发生什么的图形描述。如果很大胆,请点击我回答中的第一个链接。 @Mike “标准”格式听起来像是使用标准工具的理想机会:解析器。 -1 再次链接该答案。真的,让我们休息一下。【参考方案2】:您可能最好将 HTML 代码加载到像 this one 这样的 DOM 解析器中并搜索“定价”表。但是,只要他们更改页面布局,您所做的任何类型的抓取都可能会中断,并且未经他们同意可能是非法的。
不过,最好的方法是与网站的运营者交谈,看看他们是否有其他更可靠的数据交付形式(想到 Web 服务、RSS 或数据库导出)。
【讨论】:
我只想为我和我的朋友做这件事,以便我们可以每小时浏览一次网站。他们目前不支持任何网络服务。数据库导出...哈哈,我真的不这么认为。 是的。许多网站在其服务条款中禁止对其网站内容进行任何类型的自动浏览/下载/解析。在许多司法管辖区,这是可行的并且可以强制执行。在这种情况下不太可能有任何麻烦,但仍然值得一提。 Pekka 你有这方面的资料吗?我对这个主题很感兴趣 抓取数据并重新发布在世界大部分地区属于侵犯版权的行为。当谈到将其用于私人用途时,情况似乎没有我想象的那么明确。我遇到了这个 Google Answers 问题answers.google.com/answers/threadview?id=746810 它与印度有关,但也有一些国际意义。 即使您手动重新发布受版权保护的内容也是一种犯罪行为,我对制作自动脚本以提取它们的非法部分感兴趣 - 而不是您对这些数据所做的事情。 【参考方案3】:第一,问这个问题太详细了。第二,从网站中提取数据可能是不合法的。但是,我有提示:
使用 Firebug 或 Chrome/Safari Inspector 探索 HTML 内容和有趣信息的模式
测试您的 RegEx 以查看是否匹配。您可能需要多次执行(多次解析/提取)
通过 cURL 甚至更简单的方式编写客户端,使用 file_get_contents(注意,某些主机禁用使用 file_get_contents 加载 URL)
对我来说,我最好使用 Tidy 转换为有效的 XHTML,然后使用 XPath 提取数据,而不是 RegEx。为什么?因为 XHTML 不规则,而 XPath 非常灵活。您可以学习 XSLT 进行转换。
祝你好运!
【讨论】:
【参考方案4】:$content = file_get_contents('http://www.sparkfun.com/commerce/product_info.php?products_id=9279');
preg_match('#<tr><th>(.*)</th> <td><b>price</b></td></tr>#', $content, $match);
$price = $match[1];
preg_match('#<input type="hidden" name="quantity_on_hand" value="(.*?)">#', $content, $match);
$in_stock = $match[1];
echo "Price: $price - Availability: $in_stock\n";
【讨论】:
thsi 乍一看就像一个魅力,只是我正在寻找的简单解决方案!!!非常感谢 很容易修改以从文本中获取产品名称和其他信息....哇 10x 很多,我的意思是...这只是从许多中获取一些有意义的数据的最简单方法简单的网站。 不客气 :) 如果您有特定需求,正则表达式可以完美地从 HTML 页面中挖掘数据。如果页面结构发生变化,它们就会中断,但基于解析器的解决方案也会发生变化。 唯一可以改变的是页面上的不同链接或类似的东西,但我确实检查了很多网站,我可以判断它是否改变了设计并做出适当的改变正则表达式。 不管这是我正在寻找的答案。任何想要这样做的人....这值得 2 分钟。用于调查。【参考方案5】:这称为屏幕抓取,以防您需要谷歌搜索。
我建议您改用 dom 解析器和 xpath 表达式。首先通过 HtmlTidy 输入 HTML,以确保它是有效的标记。
例如:
$html = file_get_contents("http://www.example.com");
$html = tidy_repair_string($html);
$doc = new DomDocument();
$doc->loadHtml($html);
$xpath = new DomXPath($doc);
// Now query the document:
foreach ($xpath->query('//table[@class="pricing"]/th') as $node)
echo $node, "\n";
【讨论】:
汽车是一般旅行的最佳选择,但如果您需要拜访邻居,简单的步行就足够了。【参考方案6】:从网站中提取数据的最简单方法。我分析了我的所有数据都只包含在<h3>
标签中,所以我准备了这个。
<?php
include(‘simple_html_dom.php’);
// Create DOM from URL, paste your destined web url in $page
$page = ‘http://facebook4free.com/category/facebookstatus/amazing-facebook-status/’;
$html = new simple_html_dom();
//Within $html your webpage will be loaded for further operation
$html->load_file($page);
// Find all links
$links = array();
//Within find() function, I have written h3 so it will simply fetch the content from <h3> tag only. Change as per your requirement.
foreach($html->find(‘h3′) as $element)
$links[] = $element;
reset($links);
//$out will be having each of HTML element content you searching for, within that web page
foreach ($links as $out)
echo $out;
?>
【讨论】:
以上是关于通过 PHP 从网站中提取数据的主要内容,如果未能解决你的问题,请参考以下文章