ES6(2015)
异步解决方案 Promise
ES5 回调 callback
- function load (src,callback){
- let script = document.creatElement('script')
- script.src = src // 次操作 是 引擎默认的异步
- script.onload = () => { callback(src) }
- document.head.append(script)
- }
- load('./1.js',test)
- function test(name){
- console.log(name)
- }
- test('tt') // 先执行 test() 后执行 load()
- load('./1.js',function(st){
- load('./2.js',function(st){
- load('./3.js',test(st))
- })
- }) // 嵌套回调 回调地狱
- ES6 promise
- function load(src){
- return new Promise((resolve,reject) =>{
- let script = document.creatElement('script')
- script.src = src
- script.onload = () => resolve(src)
- script.onerror = (err) => reject(err)
- document.head.append(script)
- })
- }
- load(./1.JS)
- .then(()=>{return load(./2.JS)},(err)=>{console.log(err)})
- .then(()=>{return load(./3.JS)},(err)=>{console.log(err)}) // 平行调用
Promise 对象 基本原理
- new Promise() // 会有 pending 状态 挂起
- resolve() // 会有 fulfilled 状态
- reject() // 会有 rejected 状态 状态互斥
多个异步调用, 逐个调用 .then()
语法 : promise.then(onFulfilled,onRejected) 传入 两个函数
如果不是函数 将会是一个空的 Promise 对象.
- // 期望 load 1 2 3 顺序执行, 一步报错 后续停止执行
- // 正规写法
- load(./1.JS) // 返回 新的 Promisee 对象 调去 then
- .then(()=>{return load(./2.JS)},(err)=>{console.log(err)}) // 使用 load1 结果的 promise
- .then(()=>{return load(./3.JS)},(err)=>{console.log(err)}) // 使用 loda2 结果的 promise
- // 不正规 但可执行
- load(./1.JS)
- .then(load(./2.JS)) // 使用 laod1 结果的 promise
- .then(load(./2.JS)) // 使用 空的 promise , 因为 上次调用不符合 语法规定
- // 不正规 但可执行
- load(./1.JS)
- .then(()=>{load(./2.JS)},(err)=>{console.log(err)}) // 使用 load1 结果的 promise
- .then(()=>{load(./3.JS)},(err)=>{console.log(err)}) // 使用 空的 promise , 因为, 上次 then 没有返回任何值
- // 后 2 种 一旦 load2 报错. load3 还会执行. 是错误的结果.
- // 第 1 中 一旦 load2 报错. 将会阻断 laod3 的执行 . 是期望的结果.
返回值不是异步请求, 而是同步的结果 .resolve() .reject()
语法: Promise.resolve(value) Promise.reject(new Error())
注意 是 静态方法 Promise 类直接调用的 类方法
- function test(key){
- if(key){
- return new Promise((resolve,reject)=>{
- resolve(30)
- })
- } else if(key ===2){
- // retrun 42 会使 调用链断掉, 所以 使用 静态方法 resolve 处理正常信息使其继续调用下个 then
- return new Promise.resolve(42)
- }else {
- // retrun new Error 会使 调用链断掉. 所以 使用一个 静态方法 reject 来处理错误 阻断下次调用
- return new Promise.reject(new Error('sssss'))
- }
- }
- test(0).then((value) =>{console.log(value)},(err) => {console.log(err)})
捕获错误, 并统一处理 .catch()
- load(./1.JS)
- .then(()=>{ return load(./2.JS)}) // 第二个 reject 函数没有写
- .then(()=>{ return load(./3.JS)})
- .catch(err => console.log(err)) // 避免每次都写 reject 方法
并行异步调用: 最后一个调用结束再执行. all()
- const p1 = load(./1.JS)
- const p2 = load(./2.JS)
- const p3 = load(./3.JS)
- // 3 个异步 不论调用快慢 最后全掉用完 就会执行
- Promise.all([p1,p2,p3]).then(value =>{
- console.log(value)
- })
竞争异步调用: 第一个调用结束就执行. race()
- const p1 = load(./1.JS)
- const p2 = load(./2.JS)
- const p3 = load(./3.JS)
- // 3 个异步 只执行 最快的那个
- Promise.race([p1,p2,p3]).then(value =>{
- console.log(value)
- })
来源: http://www.bubuko.com/infodetail-3493981.html