Logische Schleife

Sasser

Erfahrenes Mitglied
Guten Abend!

Das folgende Script wird jede Minute per Cronjob aufgerufen. Die Schleife soll einen sekündlichen Cronjob ersetzen und eine Aktion ausführen, welche in dieser Sekunde (abzüglich 1 Sekunde) geplant ist. Das Script soll also die Aktion bereits 1 Sekunde zuvor ausführen.

Mein Script funktioniert soweit schon ganz gut, nur wenn z.B. in der ersten Sekunde und in der zweiten Sekunde etwas ansteht, verspätet sich die Schleife jeweils um eine Sekunde bei der nächsten Aktion. Grund hierfür ist, dass eine geplante Aktion bis zu 1.5 Sekunden dauern kann.

Deshalb nun meine Frage, wie man das Script soweit optimieren kann, sodass soetwas wie ein Puffer bis zu 2 Sekunden zwischen beiden Aktionen entsteht.

Leider komme ich bei der Logik der Schleife nicht weiter... Ich wäre für Lösungsvorschläge sehr dankbar!

PHP:
$time = time () - 1;
for ($i = "0"; $i < "60"; $i ++) {
	$parsetime = microtime ();
	$time = $time + $i;
	$result = mysql_query ( "SELECT * FROM `table` WHERE `time` = '" . $time . "'" );
     // Aktion ausführen, welche bis zu 1,5 Sekunden dauern kann
	usleep ( 1000000 - ( microtime () - $parsetime ) );
}
 
Hi

versuch es doch mal so:

PHP:
$time = time () - 1;
$overflow = 0;
for ($i = "0"; $i < "60"; $i ++) {
    $parsetime = microtime ();
    $time = $time + $i;
    $result = mysql_query ( "SELECT * FROM `table` WHERE `time` = '" . $time . "'" );
     // Aktion ausführen, welche bis zu 1,5 Sekunden dauern kann
    if( $overflow > 0 ) $overflow = 0;
    $overflow =   1000000 - ( microtime () - $parsetime ) +$overflow;
    usleep ( $overflow );
}

Erklärung: Wenn $overflow kleiner als 0 ist (das wäre der Fall wenn das Script länger als 1 sek braucht) wird in der nächsten Schleifenwartezeit diese Zeit einfach abgezogen (negativer Wert aufaddiert). So sollte die Schleife die verlorene Zeit aufholen können.
 
Vielen Dank für deine tolle und schnelle Hilfe!

Irgendwo ist noch der Wurm drin, denn dies liefert mir folgende Ausgabe:

1278028711
1278028713
1278028715
1278028717

PHP:
$overflow = 0;
for ($i = "0"; $i < "60"; $i ++) {
    $parsetime = microtime ();
    echo time ();
    // Aktion ausführen, welche bis zu 1,5 Sekunden dauern kann
    sleep ( 1.5 );
    // Aktion ausführen, welche bis zu 1,5 Sekunden dauern kann
    if( $overflow > 0 ) $overflow = 0;
    $overflow =   1000000 - ( microtime () - $parsetime ) +$overflow;
    usleep ( $overflow );
}

Nur nochmal zum Verständnis; Es ist doch jeweils immer nur 1 Sekunde Zeit, wenn also der erste Aufruf bereits über 1 Sekunde zu spät ist und die nächste ebenfalls, dann müsste doch eigentlich bei dritten Schleifendurchlauf 2 Sekunden zu spät sein oder nicht?
 
Zuletzt bearbeitet:
Angenommen dein Script startet um 00:00:00:000000.
Jetzt braucht dein Script 1,5 Sekunden. Wir liegen jetzt also bei 00:00:01:500000.
In $overflow sollte jetzt -500.000 stehen. Der nächste Schleifendurchlauf dauert wieder 1,5 Sekunden.
Wir liegen also bei 00:00:03:000000. in $overflow steht jetzt -1.000.000 (entspricht 1sekunde). Es ist also nur 1 Sekunde zu spät ;) Dein Script muss jetzt versuchen diese eine Sekunde irgendwie aufzuholen. Solange das Script allerdings jedesmal länger als 1 Sekunde läuft wird es das nicht schaffen (außer es könnte zeitreisen :suspekt: ).
Sollte es jetzt beim nächsten Durchlauf nur 0,2 Sekunden benötigen, wären wir bei 00:00:03:200000 und $overflow wäre nur noch 200000 (0.2 Sekunden hinterher).

Warum dein Script jetzt 2 Zeiten aufeinmal abarbeitet kann ich dir nicht sagen. Bist du dir da absolut sicher?

Wenn in deiner Datenbank der Timestamp 123456789 drin steht, und der aktuelle timestamp 123456789 beträgt sollten auch nur wirklich die Datensätze bearbeitet werden. Anschließend wird ja gewartet.
 
Zurück