实现一个sleep方法

1.问题:实现一个sleep方法进行等待

法一:使用Promise实现

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
// 输出结果,步骤1和步骤2,步骤4几乎同时输出,步骤3被延时1S
let sleep = ms => new Promise((resolve, reject) => {
console.log('2', new Date);
setTimeout(() => {
resolve();
}, ms);
});

console.log('1', new Date);

sleep(1000).then(() => {
console.log('3', new Date);
});

console.log('4', new Date);

法二:使用promise+async实现,避免callback形式

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
// 输出结果,步骤1,步骤2,步骤4的输出结果几乎相同;步骤3被延时1S
let sleepPromise = ms => new Promise((resolve, reject) => {
console.log('2', new Date);
setTimeout(function() {
resolve();
}, ms);
});

let wait1s = async () => {
console.log('1', new Date);
await sleepPromise(1000);
console.log('3', new Date);
}

wait1s();
console.log('4', new Date);

法三:使用promise+generator实现,注意每次调用generator构造方法都将会生成一个新的generator实例,此时将会从头开始yield.

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
// 步骤1和步骤3几乎同时同时输出,步骤2滞后1S
function *gen(ms) {
console.log('1', new Date);
yield new Promise((resolve, reject) => {
setTimeout(function() {
resolve();
}, ms);
});
}

let genIns = gen(1000);
genIns.next().value.then(() => {
console.log('2', new Date);
});
console.log('3', new Date);

关于generator,调用generator实例的next会执行到yield语句,返回的是一个对象,该对象具有两个字段,分别是value和done,value对应yield出来的值,done表示这个generator实例是否执行完毕。每次调用generator构造函数函数都会生成一个新的generator实例。

看个例子:

1
2
3
4
5
6
7
8
9
10
11
12
13
function *gen() {
yield 1;
yield 2;
return 3;
}

let gi = gen();
console.log(gi.next()); // { value: 1, done: false }
console.log(gen().next()); // { value: 1, done: false }
console.log(gi.next()); // { value: 2, done: false }
console.log(gi.next()); // { value: 3, done: true }
console.log(gen().next()); // { value: 1, done: false }
console.log(gen().next()); // { value: 1, done: false }