淺談JS三座大山之異步和單線程
單線程
但是我們在開發(fā)中,遇到請求網(wǎng)絡(luò),或者定時任務(wù)的時候,如果等待網(wǎng)絡(luò)請求結(jié)束或者定時任務(wù)結(jié)束的時候再去做其他事情,這樣頁面就會卡住,所以js有異步機制解決這個問題。
異步
異步的特點是不會阻塞后面的代碼執(zhí)行,當(dāng)同步任務(wù)執(zhí)行完畢之后,再執(zhí)行異步任務(wù)。相對的,同步會阻止代碼執(zhí)行。異步任務(wù)的應(yīng)用主要有網(wǎng)絡(luò)請求和定時任務(wù)。
異步是通過callback的方式實現(xiàn)的,在callback里面執(zhí)行異步執(zhí)行的代碼,但是有一些場景比如我們有三個網(wǎng)絡(luò)請求abc需要依次執(zhí)行,在a的回調(diào)里發(fā)起b請求,在b的回調(diào)里發(fā)起c請求,這樣會造成一種很混亂的寫法,稱之為回調(diào)地獄,可以試想一下,如果頁面邏輯過于復(fù)雜,需要依次調(diào)用10個接口,那么代碼的可讀性會非常非常差,我們?nèi)绻吹搅藙e人的這種代碼難免內(nèi)心奔跑一萬只神獸。
promise基本用法:
let fun1 = function(flag){
return new Promise((resolve,reject)=>{
if(flag){
setTimeout(() => {
resolve("success")
}, 1000);
}else{
setTimeout(() => {
reject("fail")
}, 1000);
}
})
}
fun1(true).then((res)=>{
console.log(res)//success
}).catch((res)=>{
console.log(res)
})
fun1(false).then((res)=>{
console.log(res)
}).catch((res)=>{
console.log(res)//fail
})
上面是一個最簡單的promise函數(shù),promise函數(shù)返回一個Promise對象,參數(shù)是一個函數(shù),接收兩個參數(shù)resolve和reject,這兩個參數(shù)也是函數(shù),當(dāng)執(zhí)行resolve()或者reject()的時候,函數(shù)返回.
如果執(zhí)行了resolve(),就會在調(diào)用的時候執(zhí)行then()方法,并接收resove()返回的參數(shù);
如果執(zhí)行了reject(),就會在調(diào)用的時候執(zhí)行catch()方法,并接收reject()返回的參數(shù);
用promise重新實現(xiàn)一下上面三個網(wǎng)絡(luò)請求的問題:
let callService = function(url){
return new Promise((resolve,reject)=>{
axios.get(url).then((res)=>{
resolve(res)
}).catch((err)=>{
reject(err)
})
})
}
const url1 = "/user/url1"
const url2 = "/user/url2"
const url3 = "/user/url3"
callService(url1).then((res)=>{
// do something
return callService(url2)
}).then(()=>{
// do something
return callService(url3)
}).then((res)=>{
// do something
}).catch((err)=>{
console.log(err)
})
用上面的寫法重新實現(xiàn)之后,寫法上只會有一層,而不會陷入層層的回調(diào)之中。
promise.all
promise.all可以將多個promise包裝成一個新的實例,成功的時候返回一個數(shù)組,誰先失敗返回誰的值。
promise.all方法可以幫我們處理日常開發(fā)中多接口同時調(diào)用的處理問題。
let p1 = new Promise((resolve, reject) => {
resolve('成功了')
})
let p2 = new Promise((resolve, reject) => {
resolve('success')
})
Promise.all([p1, p2]).then((result) => {
console.log(result) //['成功了', 'success']
}).catch((error) => {
console.log(error)
})
promise.race
這個方法的作用是多個接口賽跑,哪個跑得快就返回哪個
Promise.race([p1, p2]).then((result) => {
console.log(result)
}).catch((error) => {
console.log(error)
})
以上就是淺談JS三座大山之異步和單線程的詳細(xì)內(nèi)容,更多關(guān)于JS三座大山之異步和單線程的資料請關(guān)注腳本之家其它相關(guān)文章!
相關(guān)文章
在Javascript里訪問SharePoint列表數(shù)據(jù)的實現(xiàn)方法
在進行SharePoint訂制的時候經(jīng)常會遇到開發(fā)手段受限制的問題,比如通常公司都會限制服務(wù)器的訪問以及部署,很多開發(fā)都只能夠在客戶端來進行2011-05-05
javaScript年份下拉列表框內(nèi)容為當(dāng)前年份及前后50年
本文介紹的這個javaScript年份下拉列表框內(nèi)容為當(dāng)前年份及前后50年,默認(rèn)顯示當(dāng)前年份,大家可以學(xué)習(xí)下2014-05-05
alixixi runcode.asp的代碼不錯的應(yīng)用
alixixi runcode.asp的代碼不錯的應(yīng)用...2007-08-08
JS網(wǎng)頁播放聲音實現(xiàn)代碼兼容各種瀏覽器
JS網(wǎng)頁播放聲音有多種方法可以實現(xiàn),不過兼容各種瀏覽器的就沒有幾個了,不過本文的這個示例或許對大家有所幫助2013-09-09
js根據(jù)給定的日期計算當(dāng)月有多少天實現(xiàn)思路及代碼
根據(jù)給定的日期計算當(dāng)月有多少天,想必這樣的功能大家都想實現(xiàn)吧,所以本文的出現(xiàn)相當(dāng)有必要,接下來看下實現(xiàn)代碼,感興趣的朋友可以了解下,希望對你有所幫助2013-02-02

