CakePHPとsymfonyのメモリ使用量を比較してみた
「CakePHPを使っているとメモリ不足で落ちる」というなんだか微妙な話が挙がっているようなので休み中に検証してみました。CakePHPの1.1と1.2、それにsymfonyを対象としてORマッパーに意図的に大量データを取得させた場合のメモリの使用量を計測してみると、まぁほぼ妥当といってよい結果を得ることが出来ました。
とりあえず先に結論を。
- メモリの最大使用量がphp.memory_limitに達した場合はCakePHPとsymfonyも処理が止まる
- 処理に必要になるメモリの量はsymfonyもcakeもほぼ同様
- 処理速度を厳密に比較するならば データ量によって順番は変動する
- メモリの使用量を厳密に比較するならば
CakePHP1.1 < symfony < CakePHP1.2 - symfonyのsfDebugのメモリ使用量は実際の使用量から乖離している
- (参考) http://www.sooey.com/journal/2007/04/10/641/
- sfDebugの使用量がmemory_limitを下回っていっても処理が落ちないという事ではない
- ほどほどのデータ量の場合はCakePHP1.1のパフォーマンスがバランスが取れている
フレームワークの選択そのものがメモリの消費量を決定的に変えてしまう事はないでしょう。当然といえば当然ですが、実装内容に問題があるかどうかの方が影響は大きいと考えるのがよさそうです。
測定方法
memory_get_usage
/usr/local/lib/php/symfony/debug/sfWebDebug.class.php: $total_memory = sprintf('%.1f', (memory_get_usage() / 1024));
memory_get_peak_usage
cake
if (Configure::read() > 0) { echo "-- " . round(getMicrotime() - $TIME_START, 4) . "s --"; echo sprintf("-- %.1fKB --",memory_get_usage() / 1024); echo sprintf("-- %.1fKB --",memory_get_peak_usage() / 1024); echo sprintf("-- %s classes --", count(get_declared_classes())); echo sprintf("-- %s vars --", count(get_defined_vars())); }
symfony
sfContext::getInstance()->getController()->dispatch(); echo sprintf("-- %.1fKB --", memory_get_peak_usage() / 1024); echo sprintf("-- %s classes --", count(get_declared_classes())); echo sprintf("-- %s vars --", count(get_defined_vars()));
テスト結果
データ取得無し
FW | time(ms) | usage(KB) | peak_usage(KB) |
---|---|---|---|
symfony | 433 | 2532.9 | 2765.8 |
CakePHP 1.1 | 330 | 2668.3 | 2722.9 |
CakePHP 1.2 | 632 | 4452.7 | 4507.9 |
補足
検証結果で気になるポイントがいくつかありますね。
- CakePHP1.2が1.1と比較すると処理速度、メモリ使用量で肥大化しているように見える。
- 取得データが多い場合は1.2のほうがパフォーマンスが良い。
- symfonyはmemory_get_usageとmemory_get_peak_usageの開きが大きく、変数の開放などを工夫しているように見える。