Es gibt eine Möglichkeit, die setInterval
Methode von javascript, um die Methode sofort auszuführen, und wird dann mit dem Timer ausgeführt
Antworten
Zu viele Anzeigen?Wenn Sie RxJS verwenden können, gibt es etwas namens timer()
:
import { Subscription, timer } from 'rxjs';
const INITIAL_DELAY = 1;
const INTERVAL_DELAY = 10000;
const timerSubscription = timer(INITIAL_DELAY, INTERVAL_DELAY)
.subscribe(() => {
this.updateSomething();
});
// when destroying
timerSubscription.unsubscribe();
Dieses Beispiel baut auf der Antwort von @Alnitak auf, verwendet aber await Promise für eine feinere Granularität der Kontrolle innerhalb des Schleifenzyklus.
Beispiele vergleichen:
let stillGoing = true;
(function foo() {
console.log('The quick brown fox did its thing');
if (stillGoing) setTimeout(foo, 5000);
})();
foo();
Im obigen Beispiel wird foo() aufgerufen und ruft sich dann alle 5 Sekunden selbst auf.
Wenn wir jedoch irgendwann in der Zukunft stillGoing auf false setzen, um die Schleife zu stoppen, erhalten wir eine zusätzliche Protokollzeile, auch nachdem wir den Stoppbefehl erteilt haben. Das liegt daran, dass zu einem bestimmten Zeitpunkt, bevor wir stillGoing auf false setzen, die aktuelle Iteration bereits eine Zeitüberschreitung für den Aufruf der nächsten Iteration erzeugt hat.
Wenn wir stattdessen await Promise als Verzögerungsmechanismus verwenden, haben wir die Möglichkeit, die Schleife anzuhalten, bevor wir die nächste Iteration aufrufen:
let stillGoing = true;
(async function foo() {
console.log('The quick brown fox did its thing');
await new Promise(resolve => setTimeout(resolve, 5000));
if (stillGoing) foo();
})();
foo();
Im zweiten Beispiel stellen wir zunächst eine Verzögerung von 5000 ms ein, nach in dem wir den stillGoing-Wert überprüfen und entscheiden, ob der Aufruf einer weiteren Rekursion angebracht ist.
Wenn wir also stillGoing zu irgendeinem Zeitpunkt auf false setzen, wird nach dem Setzen des Wertes nicht noch eine zusätzliche Protokollzeile gedruckt.
Der Nachteil dabei ist, dass die Funktion asynchron sein muss, was für eine bestimmte Anwendung eine Option sein kann oder auch nicht.
// YCombinator
function anonymous(fnc) {
return function() {
fnc.apply(fnc, arguments);
return fnc;
}
}
// Invoking the first time:
setInterval(anonymous(function() {
console.log("bar");
})(), 4000);
// Not invoking the first time:
setInterval(anonymous(function() {
console.log("foo");
}), 4000);
// Or simple:
setInterval(function() {
console.log("baz");
}, 4000);
Ok, das ist so komplex, also lass es mich einfacher ausdrücken:
function hello(status ) {
console.log('world', ++status.count);
return status;
}
setInterval(hello, 5 * 1000, hello({ count: 0 }));
Es gibt ein Problem mit sofortigen asynchronen Aufruf Ihrer Funktion, weil Standard setTimeout/setInterval hat eine minimale Zeitüberschreitung über mehrere Millisekunden, auch wenn Sie es direkt auf 0 setzen. Es verursacht durch eine Browser-spezifische Arbeit.
Ein Beispiel für einen Code mit einer ECHTEN Nullverzögerung, der in Chrome, Safari und Opera funktioniert
function setZeroTimeout(callback) {
var channel = new MessageChannel();
channel.port1.onmessage = callback;
channel.port2.postMessage('');
}
Weitere Informationen finden Sie unter ici
Und nach dem ersten manuellen Aufruf können Sie ein Intervall mit Ihrer Funktion erstellen.