Q Code

遇事不决 可问春风 春风不语 遵循自心

重读promise

重逢Promise

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
// 状态映射表
const STATE_MAPPING = {
PENDING: 'pending',
RESOLVED: 'resolved',
REJECTED: 'rejected'
};

class MyPromise {
constructor(exector) {
this.init();
const resolve = val => {
if (this.status !== STATE_MAPPING.PENDING) {
return;
}
this.status = STATE_MAPPING.RESOLVED;
this.value = val;
this.onResolvedCallbacks.forEach(fn => fn());
};
const reject = val => {
if (this.status !== STATE_MAPPING.PENDING) {
return;
}
this.status = STATE_MAPPING.REJECTED;
this.value = val;
this.onRejectedCallbacks.forEach(fn => fn());
};

try {
exector(resolve, reject);
} catch (error) {
reject(error);
}
}

init() {
// 初始化状态pending
this.status = STATE_MAPPING.PENDING;
// promise 值
this.value = undefined;
// 成功回调集合
this.onResolvedCallbacks = [];
// 失败毁掉集合
this.onRejectedCallbacks = [];
}

handleResolve(resolve, reject, handler) {
try {
const x = handler(this.value);
if (x instanceof MyPromise) {
x.then(resolve, reject);
}
else {
resolve(x);
}
} catch (error) {
reject(error);
}
}

handleReject(resolve, reject, handler) {
try {
const x = handler(this.value);
if (x instanceof MyPromise) {
// 如果x是promise就会等待该 Promise对象的状态发生变化,才会被调用
// 并且新的 Promise 状态和 x 的状态相同。
x.then(resolve, reject);
}
else {
// 否者将结果作为promise的值,传入下一个then中的回调函数
resolve(x);
}
} catch (error) {
reject(error);
}
}

then(onFulfilled, onRejected) {
//解决onFufilled,onRejected没有传值的问题
onFulfilled = typeof onFulfilled === 'function' ? onFulfilled : v => v;
onRejected = typeof onRejected === 'function' ? onRejected : err => {throw err};
const actions = {
// 当状态已经改变时,立即执行对应的回调函数
resolved: () => {
return new MyPromise((resolve, reject) => {
// 因为Promise本身是一个异步方法,属于微任务一列,必须得在执行栈执行完了在去取他的值
// 所以所有的返回值都得包一层异步setTimeout。
setTimeout(() => {
this.handleResolve(resolve, reject. onFulfilled);
}, 0);
});
},
rejectd: () => {
return new MyPromise((resolve, reject) => {
setTimeout(() => {
this.handleReject(resolve, reject. onRejected);
}, 0);
});
},
// 当状态为pending,将回调函数插入执行队列中
pending: () => {
return new MyPromise((resolve, reject) => {
this.onResolvedCallbacks.push(() => {
setTimeout(() => {
this.handleResolve(resolve, reject, onFulfilled);
}, 0);
});
this.onRejectedCallbacks.push(() => {
setTimeout(() => {
this.handleReject(resolve, reject. onRejected);
}, 0);
})
});
}
};

// 根据当前状态执行对应函数
return actions[this.status]();
}
catch(onRejected) {
this.then(undefined, onRejected);
}
// 添加静态resolve方法
static resolve(val) {
return new MyPromise(resolve => resolve(val));
}
// 添加静态reject方法
static reject(reason) {
return new MyPromise((resolve, reject) => reject(reason));
}
// 添加静态all方法
static all(promises) {
const arr = [];
let i = 0;
function processData(index, val, resolve) {
arr[index] = val;
i++;
// 当所有promise 成功执行后,返回数组
if (i === promises.length) {
resolve(arr);
}
}
return new MyPromise((resolve, reject) => {
for (let index = 0; index < promises.length; index++) {
const curPromise = promises[index];
curPromise.then((res) => {
processData(index, res, resolve);
}, err => {
// 如果有一项失败,则直接认为失败
reject(err);
});
}
});

}
// 添加静态race方法
static race (promises) {
return new MyPromise((resolve, reject) => {
for (let p of promises) {
// 只要有一个实例率先改变状态,新的MyPromise的状态就跟着改变
this.resolve(p).then(res => {
resolve(res)
}, err => {
reject(err)
})
}
});
}
}