欢迎来到[自学php网] ①群 AG亚游集团

AG亚游集团 > php专栏 > php综合实列 >

php实现并发处理之curl篇

来源:未知 ?? 时间:2019-03-29 14:23?作者:小飞侠

[导读] php在并发处理方面的确不如java好。但是也有一些方法可以实现并发处理。比如使用curl就可以实现url的并发请求。 看到网上有人说使用curl会导致阻塞,即所有的请求数据都获取完毕后一...

php在并发处理方面的确不如java好。但是也有一些方法可以实现并发处理。比如使用curl就可以实现url的并发请求。

看到网上有人说使用curl会导致阻塞,即所有的请求数据都获取完毕后一并返回,然后再进行数据处理。而不是获取一个请求的数据就处理一个数据。其实这种说法是不对的,只能说明他在代码实现上有问题。

在php官方找了段导致阻塞的示例代码,如下:

function multiple_threads_request($nodes){ 
        $mh = curl_multi_init(); 
        $curl_array = array(); 
        foreach($nodes as $i => $url) 
        { 
            $curl_array[$i] = curl_init($url); 
            curl_setopt($curl_array[$i], CURLOPT_RETURNTRANSFER, true); 
            curl_multi_add_handle($mh, $curl_array[$i]); 
        } 
        $running = NULL; 
        do { 
            usleep(10000); 
            curl_multi_exec($mh,$running); 
        } while($running > 0); 
         
        $res = array(); 
        foreach($nodes as $i => $url) 
        { 
            $res[$url] = curl_multi_getcontent($curl_array[$i]); 
        } 
         
        foreach($nodes as $i => $url){ 
            curl_multi_remove_handle($mh, $curl_array[$i]); 
        } 
        curl_multi_close($mh);        
        return $res; 
} 
print_r(muti_thread_request(array( 
    '/wwwaff4exampleaff4com', 
    '/wwwaff4exampleaff4net', 
)));

下面是边请求url,边处理返回数据的示例代码:


/*
 * @purpose: 使用curl并行处理url
 * @return: array 每个url获取的数据
 * @param: $urls array url列表
 * @param: $callback string 需要进行内容处理的回调函数。示例:func(array)
 */
function curl($urls = array(), $callback = '')
{
    $response = array();
    if (empty($urls)) {
        return $response;
    }
    $chs = curl_multi_init();
    $map = array();
    foreach($urls as $url){
        $ch = curl_init();
        curl_setopt($ch, CURLOPT_URL, $url);
        curl_setopt($ch, CURLOPT_TIMEOUT, 1);
        curl_setopt($ch, CURLOPT_RETURNTRANSFER, 1);
        curl_setopt($ch, CURLOPT_HEADER, 0);
        curl_setopt($ch, CURLOPT_NOSIGNAL, true);
        curl_multi_add_handle($chs, $ch);
        $map[strval($ch)] = $url;
    }
    do{
        if (($status = curl_multi_exec($chs, $active)) != CURLM_CALL_MULTI_PERFORM) {
            if ($status != CURLM_OK) { break; } /如果没有准备就绪,就再次调用curl_multi_exec
            while ($done = curl_multi_info_read($chs)) {
                $info = curl_getinfo($done["handle"]);
                $error = curl_error($done["handle"]);
                $result = curl_multi_getcontent($done["handle"]);
                $url = $map[strval($done["handle"])];
                $rtn = compact('info', 'error', 'result', 'url');
                if (trim($callback)) {
                    $callback($rtn);
                }
                $response[$url] = $rtn;
                curl_multi_remove_handle($chs, $done['handle']);
                curl_close($done['handle']);
                /如果仍然有未处理完毕的句柄,那么就select
                if ($active > 0) {
                    curl_multi_select($chs, 0.5); /此处会导致阻塞大概0.5秒。
                }
            }
        }
    }
    while($active > 0); /还有句柄处理还在进行中
    curl_multi_close($chs);
    return $response;
}
 
/使用方法
function deal($data){
    if ($data["error"] == '') {
        echo $data["url"]." -- ".$data["info"]["http_code"]."\n";
    } else {
        echo $data["url"]." -- ".$data["error"]."\n";
    }
}
$urls = array();
for ($i = 0; $i < 10; $i++) {
    $urls[] = '/wwwaff4baiduaff4com/s?wd=etao_'.$i;
    $urls[] = '/wwwaff4soaff4com/s?q=etao_'.$i;
    $urls[] = '/wwwaff4sosoaff4com/q?w=etao_'.$i;
}
curl($urls, "deal");



演示网址 /demoaff4bo56aff4com/bigpipe/


注释:

1.关于curl_multi_exec函数的返回值:

返回CURLM_CALL_MULTI_PERFORM 说明curl_multi_exec需要马上被再调用一次。

返回CURLM_OK 说明已经有需要处理的数据。这时你需要进行相关处理,处理完后再次调用curl_multi_exec。

php中的curl_multi_exec是调用的curl库中的curl_multi_perform方法。代码在multi.c的230行左右。


2.此方式,虽然在获取数据和数据处理上是并行的,但是在数据处理时依然是串行的。即数据是一条条依次处理的。如果deal方法比较耗时的话,那整体会非常耗时。


最新文章

点击排行

自学PHP网专注网站建设学习,PHP程序学习,平面设计学习,以及操作系统学习

京ICP备14009008号@版权所有AG亚游集团

网站声明:本站所有视频,教程都由网友上传,站长收集和分享给大家学习使用,如由牵扯版权问题请联系站长邮箱904561283@qq.com

伊核协议前景难料 美投行预测油价将达100美元/桶 神射21分步行者射老鹰 格里芬25+8活塞斗公牛 特朗普若打响贸易战 苹果手机大盘鸡不答应 巴黎发生持刀恐袭致1名中国人受伤 外交部回应 西南石油大学4名师生野外考察遇难 遗体全部找到 力推赌场建设 安倍将博彩业视为经济良药 工信部:对WiFi万能钥匙等蹭网类程序开展调查 部分网约车司机吸毒、有前科:钱是我的 风险是你的 美“国防授权法案”鼓吹南海和台湾议题 中方回应 土俄总统就国防和能源合作达成多项共识 今日头条称遭网文恶意诋毁 起诉知乎索赔百万 台\"外长\"接受美媒采访喊话特朗普:民主不可被交易
日本军机再出事故:CH47直升机30公斤机门空中掉落 沃尔玛收购Flipkart大部分股份交易最早下周达成 韩军:韩美年度例行联演将照常进行 规模不会缩减 分析师:苹果可能将新园区建在美国东北部 CBA赔率:状态陷入迷失 辽宁主场恐再度失守 Uber拟选VMware现CFO任首席财务官 将筹备2… 五人制亚冠抽签:大连代表中国出战 遭遇日本冠军 前英国大臣称英军预算不足且已经被削弱到极点 北京大部今有小雨或雨夹雪 最高气温仅4℃ 球员使唤主教练?隆指导这待遇詹皇也享受不到 北大清华高招新政 北大:重奥赛成绩但不推奥赛热 普京今将发表年度国情咨文 这些点值得关注
美媒:中国新一代隐身轰炸机目前有两种构型在竞争 电子烟爆炸碎片插入头部 美国男子因此身亡 Windows打算按照月度收费 增加软件带来的收入 铁路春运部分增开列车回程票价打折 最低8折优惠 中甲-马修斯双响新援连场破门 永昌3-0呼和浩特 日媒:全球10大赚钱企业中国四大银行上榜 重庆12公里隧道成“魔鬼路段”:平均2天出1起车祸 科学家终于证明量子系统也存在“回归”效应 克洛普盛赞萨拉赫:他该当英超最佳 丁丁也有机会 25岁我赚了3个亿 致富小机器 笨蛋也能年赚100万txt 白手起家创业好项目 AG亚游集团