您在異步/智障時間表運行的條件語句,一旦你進入那個時間表是沒有出路的。你必須一直保持你的邏輯,包括任何遞歸活動。不過,我建議您使用承諾並將所有邏輯移至then
部分,以便進行函數式編程。
讓我們首先逐個看看我們的功能,看看如何通過承諾實現所有功能。
確定讓我們假設我們有一個名爲waitAndDoStg
的通用異步函數,它將數據和回調作爲它的兩個參數。假設我們的回調是第一種類型的錯誤。
var waitAndDoStg = (data,cb) => setTimeout(_=> cb(false, data.value),data.duration),
它永遠不會返回任何錯誤。所以經過data.duration
毫秒後,它會調用我們的回調,如cb(false, data.value)
,並將它從我們那裏獲得的數據傳回給我們。一個愚蠢的功能就是它。
所以好吧,我們需要promisfy這個異步函數。我們有一個標準的promisfy效用函數,它提供了任何異步函數,併爲我們提供了一個承諾。回調必須是第一類錯誤。
promisfy = (data,func) => new Promise((v,x) => func(data,(err,res) => err ? x(err) : v(res)));
確定的,而不是resolve
和reject
我分別使用v
和x
名。嗯,我想這是合理的使用v
爲resolve
,因爲它看起來像一個複選標記和x
罰款reject
我想。
所以這裏是其餘的代碼。它的承諾和遞歸,但我認爲這是一個非常可讀的代碼。
var promisfy = (data,func) => new Promise((v,x) => func(data,(err,res) => err ? x(err) : v(res)));
decrementByOne = n => --n,
waitAndDoStg = (data,cb) => setTimeout(_=> cb(false, data.value),data.duration),
countDownPromise = n => {n && console.log(n);
promisfy({value:n, duration:1000}, waitAndDoStg)
.then(decrementByOne)
.then(val => val !== 0 ? countDownPromise(val)
: console.log("Ignition...!"));
};
countDownPromise(3);
爲什麼?在'checkBrowser'中的代碼完成之前,'setTimeout'中的代碼將永遠不會被調用。 – aghidini
在設置超時之前調用checkbrowser? – DarkBee
我已經更新了這個問題。我有2個或更多setTimeouts。如果某些條件成立,則下一個setTimeouts不得運行。當條件滿足時, –