PHPでスクレイピングをしようと思って検索すると、Simple HTML DOM Parserというライブラリと、Goutteというライブラリが紹介されてあるようです。
昔から存在してPHPスクレイピングの定番になっているのが、Simple HTML DOM Parserらしく、紹介記事も多い。
Goutteは、パフォーマンスが良いらしいが、比較すると記事が少ない。
そこで、本記事は、パフォーマンスバトルと実装方法についてまとめておきます。
「SayMove!のランキングページから、動画のタイトルを取得する」でベンチマーク対決していただきます
1, Simple HTML DOM Parserのベンチマーク
1-1, 導入
Simple HTML DOM Parserの公式サイトにアクセスして、ダウンロードして、作業ディレクトリにsimple_html_dom.phpを配置する。
1-2, 実装
<?php
require 'simple_html_dom.php';
header('Content-Type: text/html; charset=utf-8');
$kNumberOfSamples = 10; // 何回サンプリングするか
$titles = array();
$totalOfTime = 0;
for ($i = 0; $i < $kNumberOfSamples; ++$i)
{
// 計測を開始する
$startTime = microtime(true);
// ランキングにある全てのタイトルを取得する
$html = file_get_html('http://say-move.org/ranking.php');
$rank = 0;
foreach ($html->find('h3.ranking_ttl') as $element)
{
$titles[$rank] = $element->text();
++$rank;
}
// 解放する
$html->clear();
// 計測を終了する
$totalOfTime += microtime(true) - $startTime;
echo $totalOfTime . '<br/>';
}
print_r($titles);
echo '<br/>平均実行時間: ' . $totalOfTime / $kNumberOfSamples;
unset($titles);
?>
find(‘h3.ranking_ttl’)でclass=”ranking_ttl”を取得している。
1-3, 計測結果
0.74032497406006
1.5220828056335
2.2691576480865
3.0349636077881
3.8007335662842
4.5622684955597
5.3352293968201
6.1218993663788
6.9005744457245
7.6647825241089
Array ( [0] => メカクシティアクターズ 第3話 「メカクシコード」・・略・・[29] => ダウンタウンDX 2014年5月1日放送分 )
平均実行時間: 0.76647825241089
2, Goutteのベンチマーク
2-1, 導入
GoutteのGitHubページから「You can also download the Goutte.phar file:」と書いてあるところから、goutte.pharをダウンロードして、作業ディレクトリに配置する。
2-2, 実装
<?php
require 'goutte.phar';
use Goutte\Client;
header('Content-Type: text/html; charset=utf-8');
$kNumberOfSamples = 10; // 何回サンプリングするか
$titles = array(100);
$totalOfTime = 0;
for ($i = 0; $i < $kNumberOfSamples; ++$i)
{
// 計測を開始する
$startTime = microtime(true);
// ランキングにある全てのタイトルを取得する
$client = new Client();
$crawler = $client->request('GET', 'http://say-move.org/ranking.php');
$rank = 0;
$crawler->filter('h3.ranking_ttl')->each(function($element)
{
global $titles;
global $rank;
$titles[$rank] = $element->text();
++$rank;
});
// 解放する
unset($client);
unset($crawler);
// 計測を終了する
$totalOfTime += microtime(true) - $startTime;
echo $totalOfTime . '<br/>';
}
print_r($titles);
echo '<br/>平均実行時間: ' . $totalOfTime / $kNumberOfSamples;
unset($titles);
?>
PHP初心者なので、ブロック内外でtitlesが二つ存在することになかなか気付きませんでした。
2-3, 計測結果
0.57542490959167
1.1356089115143
1.693286895752
2.2634289264679
2.8295919895172
3.4025230407715
3.9880549907684
4.5648419857025
5.1197459697723
5.6885468959808
Array ( [0] => メカクシティアクターズ 第3話 「メカクシコード」・・略・・[29] => ダウンタウンDX 2014年5月1日放送分 )
平均実行時間: 0.56885468959808
a. 結論
Goutteのほうが速いです!
メモリも計測したところ、Goutteのほうが少メモリです!
(ただしunsetでは少しメモりが漏れているようです。何か他の解放方法があるかもしれません)
「どっちがいい?」
私の結論はGoutteです。