Git Product home page Git Product logo

Comments (2)

yanggengzhen123 avatar yanggengzhen123 commented on September 2, 2024

Day4

async/await作用是用同步方式,执行异步操作
async/await实际上是用到了promise+ generator语法糖来实现的
通过yield来暂停,然后执行promise返回状态,通过内部执行.then的方式返回res给下一个next达到传参的目的,最后返回.next().value的promise状态

from trisome.

zhanglongLee avatar zhanglongLee commented on September 2, 2024

async/await 原理是什么?

概念:

async/await其实是Promise的语法糖,它是为优化then的嵌套调用而开发出来的。从字面上来看,async是“异步”的简写,await译为等待,所以我们很好理解async声明function是异步的,await等待是一个Promise对象,或者是其他任何值,并且await会暂停当前async function的执行,等待Promise的处理完成。

async声明的异步函数,把return后面的值通过Promise.resolve()返回Promise对象。

await如果等待的是Promise对象,则返回Promise的处理结果;如果是其他值,则返回该值本身。若Promise正常处理(fulfillded),其将回调的resolve函数参数作为await表达式的值;若Promise处理异常(rejected),await表达式会把Promise异常原因抛出,await表达式的值为undefined,并且await表达式后面的代码被暂停了;

实现原理

async/await是一种语法糖,用到的是ES6里的迭代函数——generator函数

generator函数

generator函数跟普通函数在写法上的区别就是,多了一个星号*,并且只有在generator函数中才能使用yield,什么是yield呢,他相当于generator函数执行的中途暂停点,比如下方有3个暂停点。而怎么才能暂停后继续走呢?那就得使用到next方法next方法执行后会返回一个对象,对象中有value 和 done两个属性

  • value:暂停点后面接的值,也就是yield后面接的值
  • done:是否generator函数已走完,没走完为false,走完为true
function* gen() {
  yield 1
  yield 2
  yield 3
}
const g = gen()
console.log(g.next()) // { value: 1, done: false }
console.log(g.next()) // { value: 2, done: false }
console.log(g.next()) // { value: 3, done: false }
// 可以看到最后一个是undefined,这取决于你generator函数有无返回值
console.log(g.next()) // { value: undefined, done: true }

实现async/await

// 模拟异步操作
function fn(nums) {
    return new Promise(resolve => {
        setTimeout(() => {
            resolve(nums * 2)
        }, 1000)
    })
}
// 生成器函数
function* gen() {
    console.time('test')
    const num1 = yield fn(1)
    const num2 = yield fn(num1)
    const num3 = yield fn(num2)
    console.timeEnd('test')
    return num3
}
function generatorToAsync(generatorFn) {
    return function () {
        // generatorFn有可能传参
        const gen = generatorFn.apply(this.arguments)
        // 模拟async函数返回一个Promise对象
        return new Promise((resolve, reject) => {
            // 定义一个go函数,用来自动执行 gen.next() 方法
            function go(key, arg) {
                let res
                try {
                    // 相当于res = gen.next('参数')
                    res = gen[key](arg) // 这里有可能会执行返回reject状态的Promise
                } catch (error) {
                    return reject(error) // 报错的话会走catch,直接reject
                }

                // 解构获得value和done
                const { value, done } = res
                if (done) {
                    // 如果done为true,说明走完了,进行resolve(value)
                    return resolve(value)
                } else {
                    // 如果done为false,说明没走完,还得继续走

                    // value有可能是:常量、Promise,Promise有可能是成功或者失败
                    return Promise.resolve(value).then(val => go('next', val), err => go('throw', err))
                }

            }
            go('next')// 第一次执行
        })
    }
}
// 测试代码
const genToAsync = generatorToAsync(gen)// 生成async函数构造器函数
const asyncRes = genToAsync()// 生成async函数
console.log(asyncRes);// async函数返回的是Promise
asyncRes.then(res=>{
    // test: 3032.6279296875 ms
    console.log(res);// 3秒后输出8
})

参考文章

from trisome.

Related Issues (20)

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. 📊📈🎉

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google ❤️ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.