基于curl数据采集之单页面并行采集函数get_htmls的使用


Posted in PHP onApril 28, 2013

用第一篇的get_html()实现简单的数据采集,由于是一个一个执行才采集数据的传输时间就会是所有页面下载的总时长,一个页面假设1秒,那么10个页面就是10秒了。所幸curl还提供了并行处理的功能。

要写一个并行采集的函数,先要了解要采集什么样的页面,对采集的页面用什么请求,才能写出一个相对常用的函数。

功能需求分析:

返回什么?

当然每一个页面的html集合成的数组

传递什么参数?

编写get_html()时,我们知道了可以用options数组来传递更多的curl参数,那么多页面同时采集函数的编写这种特性也得保留下来。

什么类型的参数?

无论是请求网页HTML,还是调用互联网api接口,get和post传递参数总是请求同一个页面或者接口,只是参数不同罢了。那么参数的类型是:

get_htmls($url,$options);

$url 是string

$options,是一个二维数组,每一个页面的参数为一个数组。

这样的话,貌似解决了问题。但是我找遍了curl的手册都没有看到get的参数传递在什么地方,所以只能$url 是数组的形式传递并且增加一个method参数

函数的原型就定下来了get_htmls($urls,$options = array, $method = ‘get');代码如下:

function get_htmls($urls, $options = array(), $method = 'get'){
     $mh = curl_multi_init();
     if($method == 'get'){//get方式传值 最常用
         foreach($urls as $key=>$url){
             $ch = curl_init($url);
             $options[CURLOPT_RETURNTRANSFER] = true;
             $options[CURLOPT_TIMEOUT] = 5;
             curl_setopt_array($ch,$options);
             $curls[$key] = $ch;
             curl_multi_add_handle($mh,$curls[$key]);
         }
     }elseif($method == 'post'){//post方式传值 
         foreach($options as $key=>$option){
             $ch = curl_init($urls);
             $option[CURLOPT_RETURNTRANSFER] = true;
             $option[CURLOPT_TIMEOUT] = 5;
             $option[CURLOPT_POST] = true;
             curl_setopt_array($ch,$option);
             $curls[$key] = $ch;
             curl_multi_add_handle($mh,$curls[$key]);
         }
     }else{
         exit("参数出错!\n");
     }
     do{
         $mrc = curl_multi_exec($mh,$active);
         curl_multi_select($mh);//减少CPU压力 注释掉CPU压力变大
     }while($active);
     foreach($curls as $key=>$ch){
         $html = curl_multi_getcontent($ch);
         curl_multi_remove_handle($mh,$ch);
         curl_close($ch);
         $htmls[$key] = $html;
     }
     curl_multi_close($mh);
     return $htmls;
 }

常用的get请求是通过改变url参数来实现的,又因为我们的函数是针对数据采集的。必然是分类采集,所以网址类似于这种:

http://www.baidu.com/s?wd=shili&pn=0&ie=utf-8

http://www.baidu.com/s?wd=shili&pn=10&ie=utf-8

http://www.baidu.com/s?wd=shili&pn=20&ie=utf-8

http://www.baidu.com/s?wd=shili&pn=30&ie=utf-8

http://www.baidu.com/s?wd=shili&pn=50&ie=utf-8

上面五个页面是很有规律的,改变的仅仅是pn的值。

$urls = array();
 for($i=1; $i<=5; $i++){
     $urls[] = 'http://www.baidu.com/s?wd=shili&pn='.(($i-1)*10).'&ie=utf-8';
 }
 $option[CURLOPT_USERAGENT] = 'Mozilla/5.0 (Windows NT 6.1; rv:19.0) Gecko/20100101 Firefox/19.0';
 $htmls = get_htmls($urls,$option);
 foreach($htmls as $html){
     echo $html;//这里得到html 就可以进行数据处理了
 }

模拟常用的post请求:

写一个post.php文件如下:

 if(isset($_POST['username']) && isset($_POST['password'])){
     echo '用户名是: '.$_POST['username'].' 密码是: '.$_POST['password'];
 }else{
     echo '请求错误!';
 }

然后调用如下:
$url = 'http://localhost/yourpath/post.php';//这里是你的路径
 $options = array();
 for($i=1; $i<=5; $i++){
     $option[CURLOPT_POSTFIELDS] = 'username=user'.$i.'&password=pass'.$i;
     $options[] = $option;
 }
 $htmls = get_htmls($url,$options,'post');
 foreach($htmls as $html){
     echo $html;//这里得到html 就可以进行数据处理了
 }

这样这个get_htmls函数也基本能实现一些数据采集的功能了

今天分享就到这里 写的不好的 讲得不清楚的 请多多指教

PHP 相关文章推荐
并发下常见的加锁及锁的PHP具体实现代码
Oct 12 PHP
php使浏览器直接下载pdf文件的方法
Nov 15 PHP
ThinkPHP实例化模型的四种方法概述
Aug 22 PHP
Smarty中的注释和截断功能介绍
Apr 09 PHP
PHP文件操作方法汇总
Jul 01 PHP
PHP实现的迷你漂流瓶
Jul 29 PHP
再谈PHP中单双引号的区别详解
Jun 12 PHP
完美利用Yii2微信后台开发的系列总结
Jul 18 PHP
yii2实现分页,带搜索的分页功能示例
Jan 07 PHP
PHP4和PHP5版本下解析XML文档的操作方法实例分析
May 20 PHP
PHP实现mysqli批量执行多条语句的方法示例
Jul 22 PHP
php微信公众号开发之答题连闯三关
Oct 20 PHP
基于curl数据采集之单页面采集函数get_html的使用
Apr 28 #PHP
基于php上传图片重命名的6种解决方法的详细介绍
Apr 28 #PHP
PHP基础学习之流程控制的实现分析
Apr 28 #PHP
PHP基础之运算符的使用方法
Apr 28 #PHP
PHP数据类型之整数类型、浮点数的介绍
Apr 28 #PHP
PHP数据类型之布尔型的介绍
Apr 28 #PHP
PHP中最容易忘记的一些知识点总结
Apr 28 #PHP
You might like
德劲1103二次变频版的打磨
2021/03/02 无线电
php 备份数据库代码(生成word,excel,json,xml,sql)
2013/06/23 PHP
ThinkPHP令牌验证实例
2014/06/18 PHP
laravel 解决Eloquent ORM的save方法无法插入数据的问题
2019/10/21 PHP
PHP pthreads v3使用中的一些坑和注意点分析
2020/02/21 PHP
JavaScript中通过闭包解决只能取得包含函数中任何变量最后一个值的问题
2010/08/12 Javascript
js编码、解码函数介绍及其使用示例
2013/09/05 Javascript
javascript中typeof的使用示例
2013/12/19 Javascript
js设置cookie过期当前时间减去一秒相当于立即过期
2014/09/04 Javascript
常用的Javascript设计模式小结
2015/12/09 Javascript
JS触发服务器控件的单击事件(详解)
2016/08/06 Javascript
探究JavaScript中的五种事件处理程序方式
2016/12/07 Javascript
微信小程序 引用其他js文件实现代码
2017/02/22 Javascript
JS按条件 serialize() 对应标签的使用方法
2017/07/24 Javascript
Vue单文件组件基础模板小结
2017/08/10 Javascript
vue父组件异步获取数据传给子组件的方法
2018/07/26 Javascript
webuploader实现上传图片到服务器功能
2018/08/16 Javascript
js使用文档就绪函数动态改变页面内容示例【innerHTML、innerText】
2019/11/07 Javascript
Vue页面切换和a链接的本质区别详解
2019/11/12 Javascript
[02:49]2018DOTA2亚洲邀请赛主赛事决赛日战况回顾 Mineski鏖战5局夺得辉耀
2018/04/10 DOTA
Python中实现字符串类型与字典类型相互转换的方法
2014/08/18 Python
详解python中init方法和随机数方法
2019/03/13 Python
python打包exe开机自动启动的实例(windows)
2019/06/28 Python
Django 对IP访问频率进行限制的例子
2019/08/30 Python
python让函数不返回结果的方法
2020/06/22 Python
全球最大的户外用品零售商之一:The House
2018/06/12 全球购物
ghd法国官方网站:英国最受欢迎的美发工具品牌
2019/04/18 全球购物
毕业生精彩的自我评价分享
2013/10/06 职场文书
商场中秋节广播稿
2014/01/17 职场文书
公休请假条
2014/04/11 职场文书
踏青活动策划方案
2014/08/19 职场文书
2014审计局领导班子民主生活会对照检查材料思想汇报
2014/09/20 职场文书
2014最新实习证明模板
2014/10/02 职场文书
2015年学生会干事工作总结
2015/04/09 职场文书
企业百日安全活动总结
2015/05/07 职场文书
2016优秀教师先进个人事迹材料
2016/02/25 职场文书