<?php
/*------------------------------*/
/*
Titre : Calcul le temps d'exécution d'un script PHP
Auteur : Eric Potvin
Date édition : 23 Sept 2005
Date mise a jour : 24 Aout 2019
Rapport de la maj:
- fonctionnement du code vérifié
Date mise a jour : 15 Fev 2026
Rapport de la maj:
- refactoring du code en PHP 8
*/
/*------------------------------*/
declare(strict_types=1);
/**
* Classe moderne pour mesurer le temps d'exécution en PHP 8.3+
*
* Améliorations par rapport à l'ancienne méthode :
* - Utilisation de hrtime() (nanoseconde) au lieu de microtime()
* - Typed properties et return types
* - Support de multiples timers simultanés
* - Format de sortie flexible
* - Precision configurable
*/
class ExecutionTimer
{
private array $timers = [];
private array $results = [];
/**
* Démarre un timer
*/
public function start(string $name = 'default'): void
{
$this->timers[$name] = hrtime(true);
}
/**
* Arrête un timer et retourne le temps écoulé
*
* @return float Temps en secondes
*/
public function stop(string $name = 'default'): float
{
if (!isset($this->timers[$name])) {
throw new RuntimeException("Timer '$name' n'a pas été démarré");
}
$elapsed = (hrtime(true) - $this->timers[$name]) / 1_000_000_000;
$this->results[$name] = $elapsed;
unset($this->timers[$name]);
return $elapsed;
}
/**
* Obtient le temps écoulé sans arrêter le timer
*/
public function elapsed(string $name = 'default'): float
{
if (!isset($this->timers[$name])) {
throw new RuntimeException("Timer '$name' n'a pas été démarré");
}
return (
hrtime(true) - $this->timers[$name]) / 1_000_000_000;
}
/**
* Formate le temps en unité appropriée
*/
public function format(float $seconds, int $precision = 4): string
{
return match (true) {
$seconds < 0.000001 => round($seconds * 1_000_000_000, $precision) .
' ns',
$seconds < 0.001 => round($seconds * 1_000_000, $precision) . ' ?s',
$seconds < 1 => round($seconds * 1000, $precision) . ' ms',
$seconds < 60 => round($seconds, $precision) . ' s',
default =>
sprintf('%d min %0.2f s', floor($seconds / 60), $seconds
% 60)
};
}
/**
* Obtient tous les résultats enregistrés
*/
public function getResults(): array
{
return $this->results;
}
/**
* Affiche un résumé formaté
*/
public function displaySummary(): void
{
echo "RÉSUMÉ DES TEMPS D'EXÉCUTION\n";
foreach ($this->results as $name => $time) {
printf("%-30s : %s\n", $name, $this->format($time));
}
}
}
// ============================================
// EXEMPLES D'UTILISATION
// ============================================
// Exemple 1 : Usage basique (ancien vs nouveau)
echo "=== EXEMPLE 1 : Usage Basique ===\n\n";
// ? ANCIEN CODE (microtime)
echo "Ancienne méthode (microtime) :\n";
$execution_time_old = $end_old - $start_old;
echo "Temps : " . round($execution_time_old, 4) . " secondes\n\n";
// ? NOUVEAU CODE (hrtime)
echo "Nouvelle méthode (hrtime) :\n";
$timer = new ExecutionTimer();
$timer->start();
$time = $timer->stop();
echo "Temps : " . $timer->format($time) . "\n\n";
// Exemple 2 : Multiples timers simultanés
echo "=== EXEMPLE 2 : Multiples Timers ===\n\n";
$timer = new ExecutionTimer();
$timer->start('boucle_1');
for ($i = 0; $i < 1000000; $i++) {
// Opération simple
}
$timer->stop('boucle_1');
$timer->start('boucle_2');
for ($i = 0; $i < 1000000; $i++) {
$x = $i * 2;
}
$timer->stop('boucle_2');
$timer->start('base_donnees_simulation');
usleep(5000); // Simule une requête DB
$timer->stop('base_donnees_simulation');
$timer->displaySummary();
// Exemple 3 : Mesure pendant l'exécution
echo "=== EXEMPLE 3 : Mesure en Temps Réel ===\n\n";
$timer = new ExecutionTimer();
$timer->start('longue_tache');
for ($i = 1; $i <= 5; $i++) {
usleep(200000); // 200ms
echo "Étape $i/5 - Temps écoulé : " . $timer->format($timer->elapsed(
'longue_tache')) . "\n";
}
$timer->stop('longue_tache');
echo "\n";
// Exemple 4 : Fonction helper simple
echo "=== EXEMPLE 4 : Fonction Helper ===\n\n";
/**
* Fonction helper pour mesurer rapidement une fonction
*/
function mesurer_execution(callable $fonction, string $nom = 'fonction'): float
{
$fonction();
$elapsed = (hrtime(true) - $start) / 1_000_000_000;
$timer = new ExecutionTimer();
echo "$nom : " . $timer->format($elapsed) . "\n";
return $elapsed;
}
mesurer_execution(function() {
for ($i = 0; $i < 500000; $i++) {
}
}, 'Calcul racine carrée');
// Exemple 5 : Comparaison de performances
echo "\n=== EXEMPLE 5 : Comparaison d'Algorithmes ===\n\n";
function bubble_sort(array $arr): array {
for ($i = 0; $i < $n - 1; $i++) {
for ($j = 0; $j < $n - $i - 1; $j++) {
if ($arr[$j] > $arr[$j + 1]) {
[$arr[$j], $arr[$j + 1]] = [$arr[$j + 1], $arr[$j]];
}
}
}
return $arr;
}
$timer = new ExecutionTimer();
// Test 1 : Bubble sort
$data_copy = $data;
$timer->start('bubble_sort');
bubble_sort($data_copy);
$timer->stop('bubble_sort');
// Test 2 : sort() natif
$data_copy = $data;
$timer->start('sort_natif');
$timer->stop('sort_natif');
$timer->displaySummary();
// Calcul du gain
$bubble_time = $timer->getResults()['bubble_sort'];
$native_time = $timer->getResults()['sort_natif'];
$gain = ($bubble_time / $native_time);
echo "Le sort() natif est " . round($gain, 1) . "x plus rapide !\n\n";
// Exemple 6 : Classe avec auto-timer (pattern decorator)
echo "=== EXEMPLE 6 : Auto-Timer (Avancé) ===\n\n";
/**
* Trait pour ajouter automatiquement un timer à n'importe quelle méthode
*/
trait TimedExecution
{
private static ExecutionTimer $globalTimer;
public static function initTimer(): void
{
self::$globalTimer = new ExecutionTimer();
}
protected function timed(string $name, callable $callback): mixed
{
if (!isset(self::$globalTimer)) {
self::initTimer();
}
self::$globalTimer->start($name);
$result = $callback();
$time = self::$globalTimer->stop($name);
echo "?? $name : " . self::$globalTimer->format($time) . "\n";
return $result;
}
}
class DataProcessor
{
use TimedExecution;
public function process(array $data): array
{
return $this->timed('Traitement des données', function() use ($data) {
// Simulation traitement
usleep(100000);
});
}
public function validate(array $data): bool
{
return $this->timed('Validation', function() use ($data) {
usleep(50000);
});
}
}
$processor = new DataProcessor();
$result = $processor->process([1, 2, 3, 4, 5]);
$valid = $processor->validate($result);
echo "\n";
?>
Fabien
31 Déc 2005 à 12:16Ce script est simple mais efficace.
Merci à l'auteur, je vais l'utilisé pour mon TPE.
Je n'oublie pas de le cité bien sure.