js 手写Promise以及then

  1. Promise状态枚举
  2. 收集状态更改的回调函数到数组里
  3. 实现resolve,reject, 注意校验状态为pending
  4. 执行Promise形参函数,传入resolve,reject
    const statusMap = {
        PENDING: 'PENDING',
        RESOLVED: 'RESOLVED',
        REJECTED: 'REJECTED'
    }
    const isPending = v => v === statusMap.PENDING
    const doAsyncTask = callback => setTimeout(() => callback(), 0);
    function MyPromise(executor) {
        if (typeof executor !== "function") throw 'executor must be a function'
        this.status = statusMap.PENDING
        this.value = null
        this.resolvedCallbacks = []
        this.rejectedCallbacks = []
        const resolve = (v) => {
            if (!isPending(this.status)) return
            if (v instanceof MyPromise) return v.then(resolve, reject)
            this.status = statusMap.RESOLVED
            this.value = v
            doAsyncTask(() => this.resolvedCallbacks.forEach(cb => cb(this.value)))
        }
        const reject = (v) => {
            if (!isPending(this.status)) return
            this.status = statusMap.REJECTED
            this.value = v
            doAsyncTask(() => this.rejectedCallbacks.forEach(cb => cb(this.value)))
        }
        try {
            executor(resolve, reject)
        } catch (error) {
            reject(error)
        }
    }

then

  1. 判断是否pending状态,判断then的形参是否函数,不是的话给出兼容处理
  2. 如果是pending,将回调收集起来
  3. 如果不是pending,返回一个promise, 判断then形参函数是否有promise类型的返回值进行分别处理
    MyPromise.prototype.then = function (onResolved, onRejected) {
        onResolved = typeof onResolved === 'function' ? onResolved : v => v
        onRejected = typeof onRejected === 'function' ? onRejected : v => { throw (v) }
        if (isPending(this.status)) {
            this.resolvedCallbacks.push(onResolved)
            this.rejectedCallbacks.push(onRejected)
            return
        }
        return new MyPromise((resolve, reject) => {
            doAsyncTask(() => {
                try {
                    const result = this.status === statusMap.RESOLVED ? onResolved(this.value) : onRejected(this.value)
                    result instanceof MyPromise ? result.then(value => resolve(value), reason => reject(reason)) : resolve(result)
                } catch (error) {
                    reject(error)
                }
            })
        })
    }
posted @ 2022-06-14 15:10  IslandZzzz  阅读(140)  评论(0)    收藏  举报