promise
time 2m41s
class MyPromise {
constructor() {
}
}
/*换成mypromise*/
// const p1 = new Promise((resolve, reject) => {
const p1 = new MyPromise((resolve, reject) => {
resolve(1);
})
p1.then((res) => {
console.log(res);
}, err => {
console.log(err);
})
/*1*/
第一步
time 5m54s
class MyPromise {
constructor(executor) {
this.state = 'pending';
this.value = undefined;
this.reason = undefined;
let resolve = (value) => {
this.state = 'fullFilled';
this.value = value
}
let reject = (reason) => {
this.state = 'rejected';
this.reason = reason;
}
executor(resolve, reject);
}
then(onFullFilled, onRejected) {
if (this.state === 'fullFilled') {
onFullFilled(this.value);
}
if (this.state === 'rejected') {
onRejected(this.reason);
}
}
}
/*换成mypromise*/
// const p1 = new Promise((resolve, reject) => {
const p1 = new MyPromise((resolve, reject) => {
resolve(1);
})
p1.then((res) => {
console.log(res);
}, err => {
console.log(err);
})
/*1*/
分析
1可以new MyPromise(参数xx),说明需要在constructor构造函数中写,定义
先把需要的方法、参数写了。参数executor,resolve, reject。参数是什么?是方法,补上resolve,reject,不然报错,补上then方法,使得函数运行不报错
2方法有了,需要干什么有了,之后需要数据,开始声明变量,this.变量可以使得在构造函数声明的变量,在构造函数外也可以使用,在then方法中也可以使用
state变量用来记录状态信息,记录状态数据,value储存resolve传入的value的值,同理
3then方法分析p1.then,传入的是两个参数, then(onFullFilled, onRejected)先写上,两个回调函数onFullFilled(this.value),判断state走相应的回调函数,
p1.then((res) => {
console.log(res);
}, err => {
console.log(err);
})
这时传到两个函数,是作为参数,作为实参传入,并不会在p1.then的时候运行,是交给p1去调用,不是直接运行。
p1调用两个回调函数,决定它们何时运行,运不运行,err的可能都不会运行,传入的实参,不一定会运行
promise是一个控制方法运行的东西,的容器,实际运行的方法,实际的方法成千上万,有各种各样的方法,这些都是传入的回调函数决定的,promise只管控制它们。具体方法的实现不管。
处理异步
time 6m35s
class MyPromise {
constructor(executor) {
this.state = 'pending';
this.value = undefined;
this.reason = undefined;
this.onFullFilledCallbacks = [];
this.onRejectedCallbacks = [];
let resolve = (value) => {
this.state = 'fullFilled';
this.value = value;
// this.onFullFilledCallbacks.forEach(fn => fn(this.value));
this.onFullFilledCallbacks.forEach(fn => fn());
}
let reject = (reason) => {
this.state = 'rejected';
this.reason = reason;
// this.onRejectedCallbacks.forEach(fn => fn(this.value));
this.onRejectedCallbacks.forEach(fn => fn());
}
executor(resolve, reject);
}
then(onFullFilled, onRejected) {
if (this.state === 'fullFilled') {
onFullFilled(this.value);
}
if (this.state === 'rejected') {
onRejected(this.reason);
}
if (this.state === 'pending') {
/* this.onFullFilledCallbacks.push(onFullFilled);
this.onRejectedCallbacks.push(onRejected);*/
this.onFullFilledCallbacks.push(() => {
onFullFilled(this.value);
});
this.onRejectedCallbacks.push(()=>{
onRejected(this.reason);
});
}
}
}
/*换成mypromise*/
// const p1 = new Promise((resolve, reject) => {
const p1 = new MyPromise((resolve, reject) => {
setTimeout(() => {
resolve(1);
}, 1000)
})
p1.then((res) => {
console.log(res);
}, err => {
console.log(err);
})
p1.then((res) => {
console.log(res);
}, err => {
console.log(err);
})
/*1 1*/
解析思路
因为异步操作setTimeout运行时,p1这是其实并没有运行完成
如同
let a = () => {
setTimeout(() => {
return 1;
})
}
let n = a();
console.log(n)
/*undefined*/
打印undefined,因为let a声明,let n声明赋值,console是同步代码,先运行
setTimeout后运行,等它们运行完之后再运行。
let n声明赋值不会等待a()里面的setTimeout运行完了,返回值了之后再去运行,所以只能拿到undefined
let n = a();运行n=undefined,之后console运行,同步代码等待执行
怎么解决这个问题?
不运行,而是放入数组
if (this.state === 'pending') {
/* this.onFullFilledCallbacks.push(onFullFilled);
this.onRejectedCallbacks.push(onRejected);*/
this.onFullFilledCallbacks.push(() => {
onFullFilled(this.value);
});
this.onRejectedCallbacks.push(()=>{
onRejected(this.reason);
});
}
异步情况,state明显是pedding,把回调函数与参数放入方法中,把回调函数运行放入方法中,方法不运行,回调函数也不会直接运行,用方法存储回调函数的运行,为了以后可以运行,之后运行这个函数,就可以直接运行回调函数了,不用传参,不管最后运不运行都要放进去,防止万一运行,万一之后用到
用数组放入函数,为了防止多个p1.then调用
onFullFilled(this.value)的value是实参,实参是在resolve(1);时传入的
这里面res是形参,不是传入的数据
p1.then((res) => {
console.log(res);
}, err => {
console.log(err);
})
再通过 this.onFullFilledCallbacks.forEach(fn => fn());遍历函数让其运行
let resolve = (value) => {
this.state = 'fullFilled';
this.value = value;
// this.onFullFilledCallbacks.forEach(fn => fn(this.value));
this.onFullFilledCallbacks.forEach(fn => fn());
}
此时then是存入回调函数不运行,运行不由then控制
resolve(1);控制运行传入的回调函数,等setTimeout运行完,resolve运行
步骤
1pedding情况的建立
2两个储存回调数组的建立
3数组储存回调方法
4从数组中提取方法
处理链式操作
time 10m20s
class MyPromise {
constructor(executor) {
this.state = 'pending';
this.value = undefined;
this.reason = undefined;
this.onFullFilledCallbacks = [];
this.onRejectedCallbacks = [];
let resolve = (value) => {
this.state = 'fullFilled';
this.value = value;
// this.onFullFilledCallbacks.forEach(fn => fn(this.value));
this.onFullFilledCallbacks.forEach(fn => fn());
}
let reject = (reason) => {
this.state = 'rejected';
this.reason = reason;
// this.onRejectedCallbacks.forEach(fn => fn(this.value));
this.onRejectedCallbacks.forEach(fn => fn());
}
executor(resolve, reject);
}
then(onFullFilled, onRejected) {
let x;
/*因为判断是同步执行的*/
const p2 = new MyPromise((resolve, reject) => {
if (this.state === 'fullFilled') {
x = onFullFilled(this.value);
// console.log('165:'+x)
resolve(x);
}
if (this.state === 'rejected') {
x = onRejected(this.reason);
resolve(x);
}
if (this.state === 'pending') {
/* this.onFullFilledCallbacks.push(onFullFilled);
this.onRejectedCallbacks.push(onRejected);*/
this.onFullFilledCallbacks.push(() => {
x= onFullFilled(this.value);
resolve(x);
});
this.onRejectedCallbacks.push(() => {
x= onRejected(this.reason);
resolve(x);
});
}
})
return p2;
}
}
/*换成mypromise*/
// const p1 = new Promise((resolve, reject) => {
const p1 = new MyPromise((resolve, reject) => {
// setTimeout(() => {
// resolve(1);
reject(1);
// }, 1000)
})
const p2 = p1.then((res) => {
// console.log(res);
return res + 1;
}, err => {
// console.log(err)
return err + 2;
})
p2.then(res => {
console.log(res,'success');
}, err => {
console.log(err,'error');
})
/*3 success*/
解析
返回的也是promise,then返回的是promise,new promise返回的也是promise,
1then返回new promise的p2,即使是第一次调用then时,也是返回一个新的promise对象,所以每次then都新建new Promise新建p2
p2
.then(res => {
console.log(res, 'success');
}, err => {
console.log(err, 'error');
})
.then(res => {
console.log(res, 'success');
}, err => {
console.log(err, 'error');
})
第二次都是undefined
x = onFullFilled(this.value);的返回值是由
const p2 = p1.then((res) => {
// console.log(res);
return res + 1;
}, err => {
// console.log(err)
return err + 2;
})
return出去的,x赋值为res+1,是then执行时,传入的回调函数,不立刻执行,之后执行的,是回调函数return的
x = onFullFilled(this.value);onFullFilled是形参,在这里面指代实参
x=(res) => {
// console.log(res);
return res + 1;
}
如果console,没有传值就是undefined
onFullFilled(this.value)中this.value相当于函数运行,传实参,res =this.value,传参并运行
为什么需要resolve(x)?
因为onFullFilled(this.value)需要新的this.value,每次链式操作拿到新的this.value,需要让它重新赋值,让this.value改变成回调函数return的值,在代码
let resolve = (value) => {
this.state = 'fullFilled';
this.value = value;
this.onFullFilledCallbacks.forEach(fn => fn());
}
中,有改变value的值,并且如果一开始是reject,之后运行也需要改变之前的state的值,由失败变成功
处理new MyPromise
time 16m35s
class MyPromise {
constructor(executor) {
this.state = 'pending';
this.value = undefined;
this.reason = undefined;
this.onFullFilledCallbacks = [];
this.onRejectedCallbacks = [];
let resolve = (value) => {
this.state = 'fullFilled';
this.value = value;
// this.onFullFilledCallbacks.forEach(fn => fn(this.value));
this.onFullFilledCallbacks.forEach(fn => fn());
}
let reject = (reason) => {
this.state = 'rejected';
this.reason = reason;
// this.onRejectedCallbacks.forEach(fn => fn(this.value));
this.onRejectedCallbacks.forEach(fn => fn());
}
// executor(resolve, reject);
try {
executor(resolve, reject);
} catch (err) {
reject(err)
}
}
then(onFullFilled, onRejected) {
/*因为判断是同步执行的*/
const p2 = new MyPromise((resolve, reject) => {
let x;
if (this.state === 'fullFilled') {
/*让resolvePromise(p2, x, resolve, reject);之后再运行,如果p2声明赋值时*/
setTimeout(() => {
try {
x = onFullFilled(this.value);
// console.log(172, x);
resolvePromise(p2, x, resolve, reject);
} catch (err) {
reject(err)
}
}, 0)
/* x = onFullFilled(this.value);
// console.log('165:'+x)
// resolve(x);
resolvePromise(p2, x, resolve, reject)*/
}
if (this.state === 'rejected') {
setTimeout(() => {
try {
x = onRejected(this.reason);
resolvePromise(p2, x, resolve, reject);
} catch (err) {
reject(err)
}
}, 0)
}
if (this.state === 'pending') {
/* this.onFullFilledCallbacks.push(onFullFilled);
this.onRejectedCallbacks.push(onRejected);*/
this.onFullFilledCallbacks.push(() => {
setTimeout(() => {
try {
x = onFullFilled(this.value);
resolvePromise(p2, x, resolve, reject);
} catch (err) {
reject(err)
}
}, 0)
});
this.onRejectedCallbacks.push(() => {
setTimeout(() => {
try {
x = onRejected(this.reason);
resolvePromise(p2, x, resolve, reject);
} catch (err) {
reject(err)
}
}, 0)
/* x = onRejected(this.reason);
// resolve(x);
resolvePromise(p2, x, resolve, reject);*/
});
}
})
return p2;
}
}
function resolvePromise(p2, x, resolve, reject) {
// console.log(192, p2, x, resolve, reject);
// console.log(209,a);
if (p2 === x) {
reject(new TypeError('typeErr'));
}
/*x可以是个方法,再return出去一个值*/
if ((typeof x === 'object' && x != null) || x === 'function') {
try {
/*thenable对象,这是处理return new Promise的情况*/
let then = x.then;
if (typeof then === 'function') {
/* then.call(x是让then需要上下文,让then的上下文,变成x,变成
* 返回的promise,相当于返回的promise.then*/
then.call(x, y => {
/*x.then值是一样的*/
// x.then(y => {
/*这时then独立调用指向window*/
// then(y=>{
console.log(250, y);
resolve(y);
}, r => {
console.log(252, r);
reject(r);
})
} else {
resolve(x);
}
} catch (err) {
reject(err);
}
} else {
resolve(x);
}
}
/*换成mypromise*/
// const p1 = new Promise((resolve, reject) => {
const p1 = new MyPromise((resolve, reject) => {
// setTimeout(() => {
resolve(1);
// reject(1);
// }, 1000)
})
const p2 = p1.then((res) => {
// console.log(res);
// return res + 1;
/*返回值是一个Promise,想要拿到里面的reject,怎么拿到,需要通过得到它xx,
* xx.then的方式得到10*/
return new MyPromise((resolve, reject) => {
reject(10);
})
}, err => {
// console.log(err)
return err + 2;
})
p2.then(res => {
console.log(266, res, 'success');
}, err => {
console.log(268, err, 'error');
})
锁
time 34m06s
function resolvePromise(p2, x, resolve, reject) {
// console.log(192, p2, x, resolve, reject);
// console.log(209,a);
let called;
if (p2 === x) {
reject(new TypeError('typeErr'));
}
/*x可以是个方法,再return出去一个值*/
if ((typeof x === 'object' && x != null) || x === 'function') {
try {
/*thenable对象,这是处理return new Promise的情况*/
let then = x.then;
if (typeof then === 'function') {
/* then.call(x是让then需要上下文,让then的上下文,变成x,变成
* 返回的promise,相当于返回的promise.then*/
then.call(x, y => {
/*x.then值是一样的*/
// x.then(y => {
/*这时then独立调用指向window*/
// then(y=>{
if (called) return;
called = true;
console.log(250, y);
resolve(y);
}, r => {
if (called) return;
called = true;
console.log(252, r);
reject(r);
})
} else {
if (called) return;
called = true;
resolve(x);
}
} catch (err) {
if (called) return;
called = true;
reject(err);
}
} else {
/*这里不需要锁了*/
resolve(x);
}
}
func
const isFunction = (value) => typeof value === 'function';
then(onFullFilled, onRejected) {
onFullFilled = isFunction(onFullFilled) ? onFullFilled : data => data;
onRejected = isFunction(onRejected) ? onRejected : err => {
throw err;
};
判断是否符合规范
time 37m38s
npm install promises-aplus-tests
promises-aplus-test app.js