JS Async / Await vs Promise vs Callbacks
Próbuję zrozumieć różnicę między tymi 3. Wywołania zwrotne i obietnice są jasne, ale nie używam async / await. Wiem, że to cukier składniowy obietnic, ale to, czego próbowałem, nie zadziałało. Dzielę się fragmentem kodu, który próbowałem to wszystko zrozumieć ...
Próbowałem z tablicą
var array = [1,2,3];
i 2 funkcje
get()wykonuje w 1 sekundę i konsolęarraypost(item)wykonuje w 2 sekundy i wypycha nowy element warray
Teraz chcę uzyskać, aby postmetoda została wykonana najpierw i getpo niej, aby wynik na konsoli [1,2,3,4]nie był[1,2,3]
ODDZWONIĆ
function get() {
setTimeout(() => console.log(array), 1000);
}
function post(item, callback) {
setTimeout(() => {
array.push(item);
callback();
}, 2000);
}
function init() {
post(4, get);
// returns [1,2,3,4] ✅
}
Działa dobrze, ale w przypadku zbyt wielu wywołań zwrotnych kod będzie bardziej niechlujny ... Więc
OBIETNICA
function get() {
setTimeout(() => console.log(array), 1000);
}
function post(item) {
return new Promise((resolve, reject) => setTimeout(() => {
array.push(item)
resolve();
}, 2000));
}
function init() {
post(4).then(get);
// returns [1,2,3,4] ✅
}
Ok z dużo czystszym kodem. Ale wciąż wiele thenpołączeń ... Teraz,
Async / Await
function get() {
setTimeout(() => console.log(array), 1000);
}
function post(item) {
setTimeout(() => {
array.push(item)
}, 2000);
}
async function init() {
await post(4);
get();
// returns [1,2,3] ❌
await post(4);
await get();
// returns [1,2,3] ❌
post(4);
await get();
// returns [1,2,3] ❌
}
O wiele bardziej przejrzysta wersja, ale tak czy inaczej, działało ... Próbowałem też tego (przekonwertuj obie funkcje ( post& get) na asynchroniczne i zadzwoń z then)
async function get() {
setTimeout(() => console.log(array), 1000);
}
async function post(item) {
setTimeout(() => {
array.push(item)
}, 2000);
}
async function init() {
post(4).then(get);
// returns [1,2,3] ❌
}
Ale nadal bezużyteczne. Więc jestem całkowicie zdezorientowany co do tej funkcji (tj. Async / await). Opisz, proszę, właśnie ten przykład. A także proszę, opowiedz mi o Promise.resolve& Promise.allw tym samym kontekście! Dzięki
Odpowiedzi
asynci awaitsą narzędziami do zarządzania obietnicami
await post(4);
Tutaj czekasz, aż zwrócona obietnica postzostanie rozwiązana.
function post(item) { setTimeout(() => { array.push(item) }, 2000); }
Jednak post nie zwraca obietnicy , więc nie robi nic użytecznego.
Miałeś już działającą implementację postz obietnicą. Więc użyj tego:
function post(item) { return new Promise((resolve, reject) => setTimeout(() => { array.push(item) resolve(); }, 2000)); }
Twoje próby asynci awaitnie używaj niczego, co rozwiązuje obietnicę po opóźnieniu . W obecnej postaci wszystkie asynczdefiniowane przez Ciebie funkcje zwracają obietnicę, która natychmiast się rozwiązuje.
Będziesz chciał użyć funkcji narzędzia, z której często możesz korzystać. Zwraca obietnicę, która jest rozpatrywana po określonej liczbie milisekund, używając setTimeout:
// utility function
let delay = ms => new Promise(resolve => setTimeout(resolve, ms));
let array = [1, 2, 3];
async function get() {
await delay(1000);
console.log(array);
}
async function post(item) {
await delay(1000);
array.push(item)
}
async function init() {
await post(4);
await get();
}
init();
console.log("wait for it...");
Podobnie jak w przypadku PROMISE .
Owiń post setTimeout w obietnicę i zwróć go.
call solution w treści settimeout.
function post(item) {
return new Promise((resolve)=>{
setTimeout(() => {
array.push(item)
resolve()
}, 2000);
})
}
wtedy możesz go używać w ten sposób:
async function init() {
await post(4);
get();
}