2016-10-31 2 views
0

zwischen ich einen Abschnitt des Codes haben, die etwa wie folgt aussieht:Code Benchmarking unterscheidet innerhalb und außerhalb der foreach-Schleife

$this->benchmark->mark('start1'); 
$timer = 0; 
foreach($x as $y) 
{ 
    $this->benchmark->mark('start2'); 
    // Some code here 
    $this->benchmark->mark('end2'); 
    $timer = $timer + $this->benchmark->elapsed_time('start2','end2'); 
} 
var_dump('Timer = '.$timer); 
$this->benchmark->mark('end1); 
var_dump('Total = '.$this->benchmark->elapsed_time('start1','end1')); 

Das bin ich so etwas wie

Timer = 0.43466 
Total = 45.34421 

gibt Wie ist das möglich? Sie sollten ziemlich identisch sein.

+0

Wird jede Iteration so schnell ausgeführt, dass sie in Ihrer Benchmark-Methode selten als abgelaufene Zeit registriert wird? – Phylogenesis

+0

Jede Iteration beträgt etwa 0,001 Sekunden. Es gibt nur ungefähr 1000 Iterationen insgesamt. – Tom

+0

Also welches Ergebnis ist richtig? .4 Sekunden oder 45 Sekunden? – DFriend

Antwort

0

Ich denke, das Problem ist ein bisschen wie die Welle-Teilchen-Dualität des Photons in der Quantenmechanik. Oder es ist ein Fehler in der PHP-Funktion microtime();

Bei dem Versuch, dies herauszufinden, vermutete ich zuerst, dass das benchmark->elapsed_time das Problem war, weil es eine Zeichenfolge zurückgibt. Aber das war überhaupt nicht beteiligt.

Um sicher zu sein, dass es nicht Teil des Problems war habe ich benchmark aus der Gleichung genommen und microtime() direkt verwendet. Die benchmark Klasse verwendet meistens nur microtime(), aber ich will sicher sein.

Hier ist meine erste Iteration

class Profiling extends CI_Controller 
{ 
    public function index() 
    { 
     $param = 3000000; 
     $start_1 = microtime(TRUE); 
     $timer = $this->long_exec_time($param); 
     $end_1 = microtime(TRUE); 
     echo "Timer"; 
     var_dump($timer); 
     $total = $end_1 - $start_1; 
     echo "Total"; 
     var_dump($total); 
    } 

    public function long_exec_time($param) 
    { 
     $timer = 0; 
     for($i = 1; $i < $param; $i++) 
     { 
      $start_2 = microtime(TRUE); 
      sqrt($i); 
      $timer += (microtime(TRUE) - $start_2); 
     } 
     return $timer; 
    } 

} 

Welche

gibt

Timer

float 3,8147616386414

Gesamt

float 6,5267660617828

Sieht aus wie dein Problem. Und es dauert tatsächlich 6+ Sekunden, um auszuführen.

Aber wenn die Funktion long_exec_time wie diese

public function long_exec_time($param) 
{ 
    $timer = 0; 
    $start_2 = microtime(TRUE); 
    for($i = 1; $i < $param; $i++) 
    { 
     sqrt($i); 
    } 
    $timer += (microtime(TRUE) - $start_2); 
    return $timer; 
} 

definiert Der Ausgang ist

Timer

float 2,3692939281464

Gesamt

float 2.3693020343781

Und ja, das ist die tatsächliche Ausführungszeit.

Das zeigt sicherlich auf die wiederholte Aufrufe an microtime(TRUE) verursacht eine längere Gesamtlaufzeit.

Aber warum die beiden Summen nicht übereinstimmen, ist ein Rätsel für mich. Logischerweise sollten sie im Wert viel näher sein. Das einzige, was mir in den Sinn kommt, ist, dass microtime eigene Probleme hat. Ich habe Berichte über Speicherlecks in der Funktion in bestimmten Umgebungen gefunden. Aber ich bin nicht sicher, wie das zu dem verrückten Unterschied beitragen würde - wenn es dazu beiträgt.

All das sagte, ich bin mir ziemlich sicher, wenn Sie die Anrufe zu $this->benchmark->mark innerhalb Ihrer foreach-Schleife entfernen, werden die Dinge viel schneller gehen.

Verwandte Themen