結論から言います。
PHPで処理時間を計測するなら、microtime関数ではなく hrtime関数 を使うのが現在の正解です。
ネット上の古い記事を「脳死」でコピペしてmicrotime(true)を使っている人をよく見かけますが、正直、その計測結果は信頼性に欠けます。
もちろん、大まかな秒数を知るだけなら十分かもしれません。
しかし、ミリ秒・ナノ秒単位のパフォーマンスチューニングが求められる現場では、そのわずかな「時刻のズレ」が致命的な判断ミスを招きます。
エンジニアとして、単に動くコードではなく、環境の変化に左右されない「精度の高い計測」を行う流儀を身につけてください。
執筆者:kazu |
|
なぜ多くのサイトで紹介されているmicrotimeは危ういのか
多くの入門サイトでは、計測の開始と終了に microtime(true) を使い、その差分を出す方法が紹介されています。
しかし、この microtime は「システム時刻(Unixタイム)」に基づいています。
ここに落とし穴があります。
外部要因による「時刻跳び」の影響を受けるから
サーバーは常に正確な時間を刻んでいるわけではありません。
NTP(Network Time Protocol)による時刻同期が走った際、時計がわずかに進んだり、あるいは戻ったりすることがあります。
もし計測中に時刻同期が発生したらどうなるでしょうか?
処理時間はマイナスになったり、異常に長い数値になったりします。
これでは、正確なボトルネックの特定など不可能です。
ダメな例:時刻同期に弱い古い計測コード
// 多くのサイトで見かける、正直おすすめしない書き方
$start = microtime(true);
// 何らかの重い処理
usleep(100000);
$end = microtime(true);
$executionTime = $end - $start;
echo "実行時間: " . $executionTime . " 秒";
このコードは「今、何時何分何秒か」の差を計算しているに過ぎません。
パフォーマンス計測において重要なのは「純粋にどれだけの時間が経過したか」であって、カレンダー上の時刻ではありません。
高精度な計測を実現するhrtime関数の最短ルート
PHP 7.3から導入された hrtime()(High Resolution Time) は、高精度な「モノトニッククロック(単調増加時計)」を利用します。
これはシステム時刻の影響を一切受けず、OSが起動してからの経過時間をナノ秒単位で返すため、計測中に時計が調整されても数値が狂いません。
実務でそのまま使えるhrtimeの標準実装
// 1. 計測開始(ナノ秒を数値として取得)
$start = hrtime(true);
// --- 計測したい処理ここから ---
for ($i = 0; $i < 1000000; $i++) {
$tmp = $i * 2;
}
// --- 計測したい処理ここまで ---
// 2. 計測終了
$end = hrtime(true);
// 3. 差分を計算(ナノ秒からミリ秒へ変換)
$nanoTime = $end - $start;
$milliTime = $nanoTime / 1e+6; // 1,000,000で割る
echo "実行時間: " . $milliTime . " ms";
このコードのポイントは、hrtime(true) と引数に true を渡している点です。
これにより、ナノ秒が int または float(環境による)で返ってくるため、単純な引き算だけで済みます。
ナノ秒単位(10億分の1秒)での計測ができるため、マイクロ秒(100万分の1秒)までしか追えない microtime よりも圧倒的に高精度です。
ボトルネックを特定するためにメモリ使用量もセットで見る
処理時間が長い原因が「アルゴリズムの複雑さ」にあるのか、それとも「メモリの使いすぎによるGC(ガベージコレクション)の発生」にあるのかを切り分ける必要があります。
時間だけを測るのは片手落ちです。
私は必ずメモリ使用量もセットで確認します。
効率厨が現場で実践する複合計測パターン
$start_time = hrtime(true);
$start_memory = memory_get_usage();
// 計測対象の処理
$data = range(1, 100000);
$end_time = hrtime(true);
$end_memory = memory_get_usage();
// 結果の出力
printf("Time: %f ms\n", ($end_time - $start_time) / 1e+6);
printf("Memory: %d KB\n", ($end_memory - $start_memory) / 1024);
このように memory_get_usage() を併用することで、「この処理でどれだけメモリを消費したか」が可視化されます。
「時間は短いがメモリを大量に食うコード」は、同時アクセスが増えた瞬間にサーバーを落とす「爆弾」になります。
時間とメモリ。
この2軸でコードを評価するのが、プロのエンジニアの規律です。
まとめ:正確な計測が良質なコードを生む
PHPの時間計測を、単なる「目安」で終わらせないでください。
カレンダー時刻に依存する microtime は、実務の計測には不向き。
PHP 7.3以降なら hrtime を使い、ナノ秒単位のモノトニッククロックで測る。
時間だけでなく memory_get_usage でメモリ負荷も同時に追跡する。
「なんとなく遅い気がする」という曖昧な感覚を捨て、確かな数値に基づいて改善を行う。
その一歩が、無駄のない、美しく効率的なシステムを創り上げることにつながります。
以上です。



コメント