Hallo Tom,
tschuldige, das war auch etwas überfallsartig ;) eddi
ist mein ShellScript, mit dem ich auf allen meinen Systemen den Aufruf von PHP-CLI erledige. D. h. PHP kann auf einem abgeschirmten System nur mit den Minimaldiensten ohne Server oder Ähnlichem seinen Dienst vollziehen. Dem Script wird als Parameter der Name eines Scriptes übergeben: eddi g-test
. Das ShellScript eddi
ruft damit folgendes auf:
env -i /home/eddi/bin/5.0.3/bin/php -f /home/eddi/phpscripte/g-test.php $@
Mit dem Aufruf an der Konsole eddi g-test 10000
übergebe ich noch den Parameter 10000, der Durchlaufanzahl bestimmt.
############################ g-test.php ###################################
<?php
ini_set('max_execution_time',200);
ini_set('memory_limit','50M');
$u wird Durch Prüfung Erstellt. Ist der zweite Parameter an der Konsole
eingegeben worden, so wird $u dieser zugewiesen; andernfalls "1" als
Durchlaufanzahl
$u=$argv[1] ? $argv[1] : 1;
test1.txt ist ein 1050112 Byte große Datei, die mit file() ein Daten-
feld mit Index 0-1535 erzeugt 1/3 der Strings ist 1.0 kB, 1/3 ist
0.67 kB und 1/3 ist 0.33 kB groß.
Die Datei kann zum Vergleich unter
http://eddi.to-grip.de/versuch/test1.txt heruntergeladen werden.
$a=file('test1.txt');
Der Prozess wird zum Vergleich ausgesetzt
sleep(1);
Beispiel für die Ausgabe von microtime(): "0.96838300 1105291560"
Die Ausgabe von microtime() wird ein Datenfeld umgewandelt
echo $start[0]; => "0.96838300" // (Sekundenbruchteil)
echo $start[1]; => "1105291560" // (wie 'echo time();')
$start=explode(' ',microtime());
Beim Beispiel ("0.96838300 1105291560") beleibend wäre die genaue Zeit
also 1105291560.96838300. Anders ausgedrückt sind das alle Zeichen von
$start[1] verbunden mit den letzen neune Zeichen von $start[0]:
$start=$start[1].substr($start[0],-9);
die erste Testreihe mit $u Durchläufen beginnt
for($i=0;$i<$u;$i++)
{
wird das Datenfeld $a durchlaufen
for($j=0;$j<count($a);$j++);
}
$end siehe $start
$end=explode(' ',microtime());
$end=$end[1].substr($end[0],-9);
Ausgabe an der Konsole:
$end - $start ergibt die exakte Dauer in Sekunden der Durchläufe $u für
for($j=0;$j<count($a);$j++); als _FOR_ mit _C_ount "for_c"
str_pad() naja ;) man ist ja Ästhet
echo 'for_c : '.str_pad(($end-$start),16)."\n";
um das Ergebnis keinsterleiweise zu beeinflussen bekommt jede funktion
die gleichen $GLOBALS übergeben, daher wird $j und $i gelöscht
unset($j,$i);
Der Prozess wird zum Vergleich ausgesetzt und abhieran wiederholen sich
die Dinge
sleep(1);
$start=explode(' ',microtime());
$start=$start[1].substr($start[0],-9);
for($i=0;$i<$u;$i++)
{
foreach($a as $v);
}
$end=explode(' ',microtime());
$end=$end[1].substr($end[0],-9);
echo 'foreach : '.str_pad(($end-$start),16)."\n";
unset($v,$i);
sleep(1);
$start=explode(' ',microtime());
$start=$start[1].substr($start[0],-9);
for($i=0;$i<$u;$i++)
{
for($j=0;$a[$j];$j++);
}
$end=explode(' ',microtime());
$end=$end[1].substr($end[0],-9);
echo 'for : '.str_pad(($end-$start),16)."\n";
es wird die Anzahl der Duchläufe ausgegeben
echo 'Durchlaeufe : '.$u;
?>
#####################Ausgabe an der Konsole ###############################
Das ist mein Code, mit dem ich Geschwindigkeitstests durchführe. Jedoch ist anzumerken, das die Kommentare herauszunehmen sind! Aus irgendeinem Grund beinflussen diese das Ergebnis...
Die schnellste Methode von -for vs foreach- ist in diesem Test allerdings:
$b=count($a);
for($i=0;$i<$u;$i++)
{
for($j=0;$j<$b;$j++);
}
Dabei wird count nicht bei jedem Aufruf folzogen, was noch mehr spart, aber
erst in Konstrukten wie
while()
for()
oder
foreach()
for()
im Realem seine Wirkung vollzieht.
Gruß aus Berlin!
eddi