Jak Mogę Czekać W Node.js (Javascript), muszę wstrzymać się na pewien czas
Rozwijam skrypt podobny do konsoli dla osobistych potrzeb... Muszę być w stanie pauzować przez dłuższy czas, ale jako węzeł.js z moich badań nie ma sposobu, aby zatrzymać się zgodnie z wymaganiami.... Jego coraz trudno odczytać informacje użytkowników off po pewnym czasie... iv widziałem tam jakiś kod, ale wierzę, że muszą mieć inne kody w środku, aby działały, takie jak: {]}
setTimeout(function() {
}, 3000);
Ale ten problem polega na tym, że potrzebuję wszystkiego po tej linii kodu, aby wykonać po okresie czas...
Na przykład,
//start-of-code
console.log('Welcome to My Console,');
some-wait-code-here-for-ten-seconds..........
console.log('Blah blah blah blah extra-blah');
//endcode.
Widziałem też takie rzeczy jak
yield sleep(2000);
/ Align = "left" / js tego nie rozpoznaje....
Jeśli ktoś jest chętny do pomocy, jest to bardzo doceniane. 23 answers
Najlepszym sposobem na to jest podział kodu na wiele funkcji, jak to:
function function1() {
// stuff you want to happen right away
console.log('Welcome to My Console,');
}
function function2() {
// all the stuff you want to happen after that pause
console.log('Blah blah blah blah extra-blah');
}
// call the first chunk of code right away
function1();
// call the rest of the code and have it execute after 3 seconds
setTimeout(function2, 3000);
Jest to rozwiązanie podobne do rozwiązania JohnnyHK, ale znacznie prostsze i łatwiejsze do rozszerzenia.Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2016-04-03 18:41:48
Umieść kod, który chcesz wykonać po opóźnieniu w setTimeout
callback:
console.log('Welcome to My Console,');
setTimeout(function() {
console.log('Blah blah blah blah extra-blah');
}, 3000);
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2013-01-10 01:44:53
Nowa odpowiedź na Stare pytanie. Dzisiaj (Styczeń 2017) jest o wiele łatwiej. Możesz użyć składni new async/await
.
Na przykład:
async function init(){
console.log(1)
await sleep(1000)
console.log(2)
}
function sleep(ms){
return new Promise(resolve=>{
setTimeout(resolve,ms)
})
}
Aby używać async/await
po wyjęciu z pudełka bez instalowania i wtyczek, musisz użyć node-v7 lub node-v8, używając znacznika --harmony
.
Więcej informacji:
- Flaga harmonii w Nodejs: https://nodejs.org/en/docs/es6/
- Wszystkie wersje NodeJS do pobrania: https://nodejs.org/en/download/releases/
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2018-07-06 20:38:29
Jest to prosta technika blokowania:
var waitTill = new Date(new Date().getTime() + seconds * 1000);
while(waitTill > new Date()){}
To blokowanie o ile nic innego nie stanie się w Twoim skrypcie (jak wywołania zwrotne). Ale ponieważ jest to skrypt konsoli, może to jest to, czego potrzebujesz!
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2016-06-01 17:51:08
Możesz użyć tego www.npmjs.com/package/sleep
var sleep = require('sleep');
sleep.sleep(10); // sleep for ten seconds
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2016-04-22 17:40:54
To pytanie jest dość stare, ale ostatnio V8 dodał Generatory, które mogą osiągnąć to, o co prosił OP. Generatory są na ogół najprostsze w użyciu do interakcji asynchronicznych z pomocą biblioteki, takiej jak suspend lub gen-run.
Oto przykład użycia suspend:
suspend(function* () {
console.log('Welcome to My Console,');
yield setTimeout(suspend.resume(), 10000); // 10 seconds pass..
console.log('Blah blah blah blah extra-blah');
})();
Podobne czytanie (poprzez bezwstydną autopromocję): o co chodzi z generatorami?.
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2015-04-23 05:32:59
Prosta i elegancka funkcja spania przy użyciu nowoczesnego Javascript
function sleep(millis) {
return new Promise(resolve => setTimeout(resolve, millis));
}
Brak zależności, brak callback hell; to wszystko: -)
Biorąc pod uwagę przykład podany w pytaniu, tak czekalibyśmy między dwoma logami konsoli:
async function main() {
console.log("Foo");
await sleep(2000);
console.log("Bar");
}
main();
"wadą" jest to, że Twoja główna funkcja musi być również async
. Ale biorąc pod uwagę, że już piszesz nowoczesny kod Javascript, powinieneś używać async
/await
cały Twój kod, więc to naprawdę nie jest problem. Wszystkie nowoczesne przeglądarki dzisiaj obsługują to.
Dając trochę wgląd w funkcję sleep
dla tych, które nie są używane do async/await
, Możesz również napisać to tak:
async function sleep(millis) {
return new Promise(function (resolve, reject) {
setTimeout(function () { resolve(); }, millis);
});
}
Użycie operatora fat arrow sprawia jednak, że jest on jeszcze mniejszy (i bardziej elegancki).
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2018-08-20 14:33:29
Najkrótsze rozwiązanie bez żadnych zależności:
await new Promise(done => setTimeout(done, 5000));
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2018-03-06 20:47:32
Ostatnio stworzyłem prostszą abstrakcję o nazwie czekaj.dla wywoływania funkcji asynchronicznych w trybie synchronizacji (w oparciu o node-fibers). Istnieje również wersja oparta na nadchodzących generatorach ES6.
Https://github.com/luciotato/waitfor
Using wait.dla , można wywołać dowolną standardową funkcję asynchroniczną nodejs, tak jakby była funkcją synchronizacji, bez blokowania pętli zdarzeń węzła.
Możesz kodować sekwencyjnie, kiedy tego potrzebujesz, co jest (zgaduję) idealne do uprość skrypty do użytku osobistego.
Using wait.dla twój kod będzie:
require('waitfor')
..in a fiber..
//start-of-code
console.log('Welcome to My Console,');
wait.miliseconds(10*1000); //defined in waitfor/paralell-tests.js - DOES NOT BLOCK
console.log('Blah blah blah blah extra-blah');
//endcode.
Również każda funkcja asynchroniczna może być wywołana w trybie Sync. Sprawdź przykłady.
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2013-09-06 13:58:46
Na Linuksie/nodejs to mi działa:
Const spawnSync = require ('child_process').spawnSync;
Var sleep = spawnSync ('sleep', [1.5]);
Blokuje, ale nie jest zajętą pętlą oczekiwania.
Podany czas jest w sekundach, ale może być ułamkiem. Nie wiem, czy inne OS mają podobną komendę.
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2016-11-18 18:50:04
Chciałem asynchronicznego snu, który działał w systemach Windows i Linux, bez blokowania mojego procesora długą pętlą while. Próbowałem pakietu sleep, ale nie instalował się na moim pudełku Windows. Skończyło się na używaniu:
Https://www.npmjs.com/package/system-sleep
Aby go zainstalować, wpisz:
npm install system-sleep
W Twoim kodzie,
var sleep = require('system-sleep');
sleep(10*1000); // sleep for 10 seconds
Działa jak urok.Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2017-01-13 18:56:36
Jeśli chcesz "kodować golfa", możesz zrobić krótszą wersję niektórych innych odpowiedzi tutaj:
const sleep = ms => new Promise(resolve => setTimeout(resolve, ms));
Ale tak naprawdę idealną odpowiedzią moim zdaniem jest użycie biblioteki util
Node i jej funkcji promisify
, która jest zaprojektowana do tego typu rzeczy (Tworzenie wersji opartych na obietnicach wcześniej istniejących rzeczy nie opartych na obietnicach):
const util = require('util');
const sleep = util.promisify(setTimeout);
W obu przypadkach możesz wstrzymać po prostu za pomocą await
, aby wywołać funkcję sleep
:
await sleep(1000); // sleep for 1s/1000ms
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2017-10-24 00:38:40
Ponieważ silnik javascript (v8) uruchamia kod w oparciu o sekwencję zdarzeń w event-queue, nie ma ścisłego wymogu, aby javascript dokładnie wyzwalał wykonanie po określonym czasie. Oznacza to, że gdy ustawisz kilka sekund na późniejsze wykonanie kodu, Kod wyzwalający opiera się wyłącznie na sekwencji w kolejce zdarzeń. Uruchomienie wykonania kodu może więc zająć więcej niż określony czas.
So Node.js follows,
process.nextTick()
Aby uruchomić kod później zamiast setTimeout (). Na przykład,
process.nextTick(function(){
console.log("This will be printed later");
});
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2013-06-16 06:33:20
Z obsługą ES6 Promise
s, możemy ich używać bez pomocy osób trzecich.
const sleep = (seconds) => {
return new Promise((resolve, reject) => {
setTimeout(resolve, (seconds * 1000));
});
};
// We are not using `reject` anywhere, but it is good to
// stick to standard signature.
Następnie użyj go tak:
const waitThenDo(howLong, doWhat) => {
return sleep(howLong).then(doWhat);
};
Zauważ, że funkcja doWhat
staje się wywołaniem zwrotnym resolve
wewnątrz new Promise(...)
.
Zauważ również, że jest to asynchroniczny sen. Nie blokuje pętli zdarzeń. Jeśli chcesz zablokować sen, użyj tej biblioteki, która realizuje blokowanie snu za pomocą wiązań C++. (Chociaż potrzeba blokowania uśpienia w Node, takim jak środowiska asynchroniczne, jest Rzadki.)
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2017-07-31 23:27:13
let co = require('co');
const sleep = ms => new Promise(res => setTimeout(res, ms));
co(function*() {
console.log('Welcome to My Console,');
yield sleep(3000);
console.log('Blah blah blah blah extra-blah');
});
Powyższy kod jest efektem ubocznym rozwiązania asynchronicznego problemu wywołania zwrotnego Javascript. Jest to również powód, dla którego uważam, że Javascript jest użytecznym językiem w backendzie. W rzeczywistości jest to najbardziej ekscytujące ulepszenie wprowadzone do współczesnego Javascript moim zdaniem. Aby w pełni zrozumieć, jak to działa, należy w pełni zrozumieć sposób działania generatora. Słowo kluczowe function
, po którym następuje *
, jest nazywane funkcją generatora we współczesnym Javascript. Pakiet npm co
dostarczono funkcję runner do uruchomienia generatora.
Zasadniczo funkcja generatora umożliwiała wstrzymanie wykonania funkcji za pomocą słowa kluczowego yield
, jednocześnie yield
w funkcji generatora umożliwiała wymianę informacji pomiędzy wewnątrz generatora a wywołującym. Dzięki temu wywołujący mógł wyodrębnić dane z promise
z asynchronicznego wywołania i przekazać rozwiązane dane z powrotem do generatora. Skutecznie wykonuje asynchroniczne wywołanie synchroniczne.
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2017-03-08 11:57:52
Jeśli musisz tylko zawiesić w celu testowania, wykonaj bieżący wątek, spróbuj tego:
function longExecFunc(callback, count) {
for (var j = 0; j < count; j++) {
for (var i = 1; i < (1 << 30); i++) {
var q = Math.sqrt(1 << 30);
}
}
callback();
}
longExecFunc(() => { console.log('done!')}, 5); //5, 6 ... whatever. Higher -- longer
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2016-11-29 09:19:15
Proste będziemy czekać 5 sekund na jakieś zdarzenie (które będzie wskazywane przez zmienną done ustawioną na true gdzie indziej w kodzie) lub gdy timeout wygaśnie, że będziemy sprawdzać co 100ms
var timeout=5000; //will wait for 5 seconds or untildone
var scope = this; //bind this to scope variable
(function() {
if (timeout<=0 || scope.done) //timeout expired or done
{
scope.callback();//some function to call after we are done
}
else
{
setTimeout(arguments.callee,100) //call itself again until done
timeout -= 100;
}
})();
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2017-03-22 14:54:04
Dla niektórych osób akceptowana odpowiedź nie działa, znalazłem inną odpowiedź i działa dla mnie: Jak mogę przekazać parametr do wywołania zwrotnego setTimeout ()?
var hello = "Hello World";
setTimeout(alert, 1000, hello);
'hello' jest parametrem przekazywanym, możesz przekazać wszystkie parametry po upływie czasu timeout. Dzięki @ Fabio Phms za odpowiedź.
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2017-05-23 12:18:24
Zobacz readline-sync ( https://www.npmjs.com/package/readline-sync )
Zainstaluj za pomocą npm install readline-sync
var readlineSync = require('readline-sync');
while(true) {
var input = readlineSync.question("What is your input?");
if(input === 'exit') {
process.exit();
} else {
console.log("Your input was " + input);
}
}
Może nie najlepsza praktyka, ale robi to za mnie
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2017-08-26 22:01:46
To jest chwila.moduł js oparty na podejściu dirty blocking sugerowanym przez @atlex2 . Użyj tego tylko do testów .
const moment = require('moment');
let sleep = (secondsToSleep = 1) => {
let sleepUntill = moment().add(secondsToSleep, 'seconds');
while(moment().isBefore(sleepUntill)) { /* block the process */ }
}
module.exports = sleep;
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2017-11-08 14:11:34
Inne odpowiedzi są świetne, ale pomyślałem, że wezmę inny takt.
Jeśli wszystko czego naprawdę szukasz to spowolnienie konkretnego pliku w Linuksie:
rm slowfile; mkfifo slowfile; perl -e 'select STDOUT; $| = 1; while(<>) {print $_; sleep(1) if (($ii++ % 5) == 0); }' myfile > slowfile &
Node myprog slowfile
To będzie spać 1 sek co pięć linii. Program node będzie działał tak wolno jak writer. Jeśli robi inne rzeczy, będą kontynuować z normalną prędkością.
Mkfifo tworzy rurę typu first-in-first-out. To sprawia, że to działa. Linia Perla będzie pisać tak szybko, jak chcesz. $ / =1 mówi: nie buforuj wyjścia.Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2017-08-05 14:24:14
Aby uzyskać więcej informacji na temat
yield sleep(2000);
Powinieneś sprawdzić Redux-Saga . Ale jest to specyficzne dla Twojego wyboru Redux jako ramy modelu (chociaż absolutnie nie jest to konieczne).
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2016-09-09 09:24:46
Ułożyłem, po przeczytaniu odpowiedzi na to pytanie, prostą funkcję, która może również zrobić callback, jeśli potrzebujesz, że:
function waitFor(ms, cb) {
var waitTill = new Date(new Date().getTime() + ms);
while(waitTill > new Date()){};
if (cb) {
cb()
} else {
return true
}
}
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2016-11-06 08:08:38