1. 程式人生 > 實用技巧 >Promise,Promise.then,Promise.all,Promise.race

Promise,Promise.then,Promise.all,Promise.race

Promise

1.什麼是Promise?

Promise 是一個物件。

2.promise的作用?

promise主要用於進行非同步操作。

在Promise未出現前,我們通常是使用巢狀回撥函式來解決的。但是使用回撥函式來解決非同步問題,簡單還好說,但是如果問題比較複雜,就會進入回撥地獄。

3.Promise的三種狀態?

等待態(Pending):初始狀態

執行態(Fulfilled):操作成功狀態

拒絕態(Rejected):操作失敗狀態

promise狀態的變化:單向的從pending變為fulfilledpending變為rejected。但是狀態一旦改變就不會再變了。

4.使用Promise的優缺點?

優點:讓回撥函式變成了鏈式的寫法,避免了回撥地獄,程式的流程看的更清楚。

缺點:①無法取消Promise,一旦新建就立即執行,無法中途取消

②如果不設定回撥函式。Promise內部丟擲的錯誤,不會反應到外部。

5.Promise的建立



varmyPromise=newPromise((resolve,reject)=>{
//進行非同步處理
//呼叫resolve或者reject
})

Promise有倆個引數resolvereject

resolve的作用是將Promise的狀態從等待狀態轉變成成功狀態,並把返回的資料傳出來,reject的作用是將Promise的狀態從等待狀態轉變成失敗狀態,將錯誤的資訊返回。

Promise是物件,物件和函式的區別就是,物件的狀態可以一直保持。

6.Promise的Api介面

  1. Promise.resolve()

  2. Promise.reject()

  3. Promise.prototype.then()

  4. Promise.prototype.catch()

  5. Promise.all() // 所有的完成

  6. Promise.all([p1,p2,p3])

Promise.then()

1.promise.then()

對於已經例項化的Promise物件可以呼叫promise.then()方法,傳遞resolve和reject方法作為回撥。

2.promise.then語法

promise.then(onFuilled,onRejected)。也可寫成promise.then(onFuilled).catch(onRejected). 3.promise.then回撥函式只能執行一次,且返Promise物件。 4.promise.then有兩個引數:分別是promise的成功和失敗情況的回撥函式。 5.promise.then語法
var p=new Promise((resolve,reject)=>{
            resolve('成功');
            // reject(new Error("失敗了"))
        });
        p.then(value=>{
            console.log(value);
        }).catch(reason=>{
            console.log(reason);
        })

注意:如果函式丟擲的錯誤返回一個拒絕的Promise,則then將返回一個拒絕的Promise

Promise.all()

1.promise.all()方法用於將多個promise例項,包裝成一個新的例項

var p=new Promise([p1,p2,p3]);

 promise.all()中的例項不一定是陣列,但是必須要有iterator介面(Array,Map,Set,String等) 

2.promise.all的使用

當例項的狀態變成Fulfilled狀態,例項P才會變成Fulfilled'狀態,將所有例項的返回值傳遞給p的回撥函式。

但是當例項中有一個被rejected,p的狀態就變成rejected狀態,此時第一個被rejected的例項的返回值傳遞給p的回撥函式。

通俗點就是都成功才會呼叫成功的回撥函式。一旦有一個失敗就呼叫失敗的回撥函式。
 var p1 = new Promise((resolve, reject) => {
            resolve('成功');
        })
 var p2 = new Promise((resolve, reject) => {
            resolve('success');
        })
 var p3 = Promise.reject('失敗');
        
        var p = new Promise.all([p1, p2, p3]);
        var pp = new Promise.all([p1, p2,]);
        p.then(success => {
            console.log("success");
        }).catch(error => {
            console.log(error)//失敗
        })
        pp.then(success => {
            console.log("success");//成功 success
        }).catch(error => {
            console.log(error)
        })

3.Promise.all()的應用場景

比如在支付的時候要判斷支付的餘額和商品的庫存,當顧客的餘額足夠並且商品的庫存有餘是才可以支付成功,有一個情況不符合就無法完成支付。

Promise.race()

race:賽跑; 速度競賽; 競爭; 角逐;

也是將多個Promise例項包裝成一個新的Promise例項

var p=new Promise([p1,p2,p3]);

但是與Promise.all()不同的是,所有例項中只要有一個狀態改變,p就跟著改變,率先改變的例項的返回值傳遞給p的回撥函式;

   var p1 = new Promise((resolve, reject) => {
           setTimeout(()=>{
                resolve('success');
           },3000)
        })
        var p2 = new Promise((resolve, reject) => {
           setTimeout(()=>{
                reject('失敗')
           },1000)
        })

        var p=new Promise.race([p1,p2]);
        p.then(success => {
            console.log("success");
        }).catch(error => {
            console.log(error);//reject 失敗  p2的狀態率先改變
})

Promise.resolve ()

可以將不是Promise的物件轉成Promise物件;生成的新的例項,例項狀態為fulfilled,就會立即執行.

若promise.resolve()裡面的引數本來就是Promise物件就會原封不動的返回。

var p=promise.resolve(hello);//p為promise物件

例項的引數還是回撥函式的引數

var p = promise('hello');
        p.then(res => {
            console.log(res);//hello
        })

Promise.reject()

Promise.reject()方法也會返回一個新的Promise例項,例項的狀態為rejected

var p = promise('出錯了');
        p.then(res => {
            console.log(res);//出錯了
        })
p2的狀態率先改變