Skip to content

第 42 题:实现一个 sleep 函数,比如 sleep(1000) 意味着等待1000毫秒,可从 Promise、Generator、Async/Await 等角度实现 #63

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Open
suguoyao opened this issue Mar 27, 2019 · 46 comments

Comments

@suguoyao
Copy link

const sleep = (time) => {
  return new Promise(resolve => setTimeout(resolve, time))
}

sleep(1000).then(() => {
    // 这里写你的骚操作
})
@suguoyao
Copy link
Author

const sleep = (time) => {
  return new Promise(resolve => setTimeout(resolve, time))
}

async function sleepAsync() {
  console.log('fuck the code')
  await sleep(1000)
  console.log('fuck the code again')
}

sleepAsync()

@lvtraveler
Copy link

lvtraveler commented Mar 27, 2019

4种方式:

//Promise
const sleep = time => {
  return new Promise(resolve => setTimeout(resolve,time))
}
sleep(1000).then(()=>{
  console.log(1)
})

//Generator
function* sleepGenerator(time) {
  yield new Promise(function(resolve,reject){
    setTimeout(resolve,time);
  })
}
sleepGenerator(1000).next().value.then(()=>{console.log(1)})

//async
function sleep(time) {
  return new Promise(resolve => setTimeout(resolve,time))
}
async function output() {
  let out = await sleep(1000);
  console.log(1);
  return out;
}
output();

//ES5
function sleep(callback,time) {
  if(typeof callback === 'function')
    setTimeout(callback,time)
}

function output(){
  console.log(1);
}
sleep(output,1000);

参考:

@zeroone001
Copy link

const sleep = (time) => {
    return new Promise((resolve, reject) => {
        setTimeout(resolve, time);
    });  
};
sleep(1000).then(() => {
    console.log('sleep end');
});

大家在工作中是使用Promise最多吗

@jefferyE
Copy link

jefferyE commented Mar 27, 2019

function sleep(time) {
  function* gen () {
     yield new Promise((resolve, reject) => {
         setTimeout(() => {
             resolve()
         }, time)
     })
   }
   return gen().next().value;
}
sleep(1000).then(() => {
   console.log('sleep end');
});

@Peizy
Copy link

Peizy commented Mar 27, 2019

function sleep1(time) {
   return new Promise(resolve => {
       setTimeout( resolve  , time);
     });
   }
function sleep2(time) {
  const start = Date.now();
  let stop;
  while (true) {
    stop = Date.now();
    if (stop - start > time) break;
  }
}

async function exec() {
  console.log("11111111111111111111111111111");
  await sleep1(1000);
  console.log("222222222222222222222222222222");
  sleep2(1000);
  console.log("333333333333333333333333333333");
}
exec();

@GeekQiaQia
Copy link

/**
   * DailyIssue42:
   42:实现一个 sleep 函数,
   比如 sleep(1000) 意味着等待1000毫秒,可从 Promise、Generator、Async/Await 等角度实现:
   // Promise:
   *https://blog.csdn.net/ImagineCode/article/details/81089107
   * */

  let sleep={
      // sleep  in promise;
      sleepInPromise:function(delayTime){
          return new Promise((resolve,reject)=>{
              setTimeout(function () {
                  resolve('do something in promise');
              },delayTime)
          })
      },
      sleepInGenerator:function *(delayTime){

          yield new Promise(function(resolve,reject){
              setTimeout(function(){
                  resolve('do in generator');
              },delayTime);
          })

      },
      sleepInES5:function(callback,delayTime){
          if( typeof callback==='function'){
              setTimeout(()=>{
                  callback();
              },delayTime);
          }
      }

  }
  // 执行函数;
  function doSomeThing(){
      console.log('sleepInES5');
  }
  sleep.sleepInES5(doSomeThing,1000);

  // 执行函数
  sleep.sleepInPromise(1000)
      .then(function (res) {
          console.log(res);
      })
      .catch(function (err) {
          console.log(err);
      })
  // 执行函数
  sleep.sleepInGenerator(1000).next().value
      .then(res=>{
          console.log(res);
      })
  // async 函数声明;
   async function sleepAsync(delayTime){
      let result;
      try{
           result= await sleep.sleepInPromise(delayTime);
      }catch(e){
          console.log(e);
      }
      console.log(result);
  }
  // 执行函数
  sleepAsync(1000);

@aeolusheath
Copy link

// 方法一

function sleep(time) {
  return new Promise((resolve, reject) => {
    setTimeout(() => {
      resolve(time)
    }, time)
  })
}

sleep(5000).then((time) => { console.log(`你睡了${time / 1000}s,然后做你的事情`) })

// 方法二

function async sleep2(time) {
  await sleep(time)
  // then do you thing
  console.log(`你睡了${time / 1000}s,然后做你的事情`)
  // async 函数返回的是一个promise对象
}

// 方法三
// 通过generator 还是返回一个promise,这个不知道具体的意义,这和返回一个普通的promise有区别么

function* sleep3(time) {
  yield new Promise(resolve => {
    setTimeout(resolve, time)
  })
}

sleep3(5000).next().value.then(() => { console.log("睡了一会儿,然后做你做的事情")})

// 方法四
// 通过传统的setTimeout去做

function sleep4(func, time) {
  setTimeout(func, time)
}

@formattedzzz
Copy link

难道就不能不用定时器吗

function sleep (time) {
	var now = +Date.now()
	while (+Date.now() - now <= time) {}
	return
}
console.time(1)
sleep(2000)
console.log(123)
console.timeEnd(1)

console.time(1)
sleep(3000)
console.log(456)
console.timeEnd(1)
// 123
// 2000.244140625ms
// 456
// 3001.861328125ms

@tgxhx
Copy link

tgxhx commented Mar 29, 2019

在9012年的今天,其他都是异端,请使用async/await。

@te3
Copy link

te3 commented Mar 29, 2019

//1. Promise
const sleep1 = time => new Promise(resolve => setTimeout(resolve, time));

//2.without Promise
const sleep2 = time => ({
  then: cb => {
    setTimeout(cb, time);
  }
});

//3. Generator, without Promise code
const sleep3 = time => {
  function* gen() {
    yield {
      then: cb => {
        setTimeout(cb, time);
      }
    };
  }
  return gen().next().value;
};

//4. async/await without Promise code and Generator
const sleep4 = async time=>{
    await sleep2(time);
}

//call
(async ()=>{
    console.time('sleep1');
    await sleep1(1000);
    console.timeEnd('sleep1');

    console.time('sleep2');
    await sleep2(1000);
    console.timeEnd('sleep2');

    console.time('sleep3');
    await sleep3(1000);
    console.timeEnd('sleep3');

    console.time('sleep4');
    await sleep4(1000);
    console.timeEnd('sleep4');
})();

//typeof callback === "hell"

@neofanfei
Copy link

function timeout (time) {
	return new Promise(function(res,rej){
		setTimeout(res,time)
	})
}
async function sleep (time) {
	console.log(1)
	await timeout(time)
	console.log(2)
}

@coolliyong
Copy link

Javascript 模拟实现 Sleep 函数

这是一个伪命题,无法挂起 JS 进程,在 sleep 之后再继续,应该是写一个 sleep 的异步,通过异步实现

  • 回调函数版本
//回调函数实现
const sleepCb = (wait, cb) => setTimeout(cb, wait);
sleepCb(5500, () => {
  console.log("cb");
});
  • Promise
const sleep = wait => new Promise(resolve => setTimeout(resolve, wait));
sleep(1500).then(res => {
  // sleep 之后干的事
  console.log("sleep");
});
  • Generator 基于 promise
function* sleep2(wait) {
  yield new Promise(resolve => setTimeout(resolve, wait));
}
sleep2(2500)
  .next()
  .value.then(() => {
    // sleep 之后干的事
    console.log("sleep2");
  });
  • async/await 基于 promise
async function sleep3(wait) {
  await new Promise(resolve => {
    setTimeout(resolve, wait);
  });
}
sleep3(3500).then(() => {
  console.log("sleep3");
});

@chaijinsong
Copy link

看题目以为是实现类似于java的sleep

sleep(1000);
console.log('sleep之后做的事');

后来实在想不出来怎么实现,看了大家的答案,发现是我想多了,,确实没法实现这样的sleep

@nailfar
Copy link

nailfar commented Jun 20, 2019

function sleep(duration){
  startTime = Date.now();
  while ( Date.now() - startTime < duration );
}
sleep(3000);
console.info("sleeped 3sec!") 

@chenzesam
Copy link

4种方式:

//Promise
const sleep = time => {
  return new Promise(resolve => setTimeout(resolve,time))
}
sleep(1000).then(()=>{
  console.log(1)
})

//Generator
function* sleepGenerator(time) {
  yield new Promise(function(resolve,reject){
    setTimeout(resolve,time);
  })
}
sleepGenerator(1000).next().value.then(()=>{console.log(1)})

//async
function sleep(time) {
  return new Promise(resolve => setTimeout(resolve,time))
}
async function output() {
  let out = await sleep(1000);
  console.log(1);
  return out;
}
output();

//ES5
function sleep(callback,time) {
  if(typeof callback === 'function')
    setTimeout(callback,time)
}

function output(){
  console.log(1);
}
sleep(output,1000);

参考:

其实都是 promise

@ouyinheng
Copy link

ouyinheng commented Jul 12, 2019

function sleep(wait) {
    let date = new Date().getTime();
    console.log('wait...')
    while ((new Date().getTime()) - date < wait) {
      continue;
    }
}

@qiannianchong25
Copy link

sleep实现无外乎同步和异步两种方法。同步可以用for循环或者while让它在等待时间内啥也不干;异步就是利用setTimeout来做定时。如果后序处理很复杂,可以考虑结合promise来实现。毕竟,promise解决回调地狱之类的问题还是很有一套的。代码就不贴了,上面都是。免得搞一大片的重复代码,实在没啥必要。

@martinshao
Copy link

在9012年的今天,其他都是异端,请使用async/await。

你这人真极端,文革期间应该是抛头颅洒热血的好青年。。。

@NANAYWY
Copy link

NANAYWY commented Jul 19, 2019

var sloop=function(time){
  return new Promise(function (resolve, reject) {
   setTimeout(function(){
     resolve(time)
   },time)
  })
  }
  sloop(1000).then(function (value) {
    console.log(value)
  })
~~~ 虽然我是菜鸟,但我还是要记录一下我的答案

@thinkfish
Copy link

thinkfish commented Jul 21, 2019

let sleep = function (time){
    return new Promise((resolve,reject)=>{
       setTimeout(resolve,time)
  })
}
sleep(1000).then(res=>{
    //do something
})

@mongonice
Copy link

mongonice commented Jul 24, 2019

promise方法

function sleep(time) {
  return new Promise(resolve => {
    setTimeout(() => {
      resolve()
    }, time)
  })
}
sleep(1000).then((data) => {
    // do something
})

async/await方法

async function sleep(time) {
  await new Promise(resolve => {
    setTimeout(resolve, time)
  })
 // do something
     ...
}

generator

function * sleep (time) {
    yield new Promise(resolve => {setTimeout(resolve, time)})
}
sleep(1000).next().value.then(() => {
    console.log('已经等待1s')
})

@Rel1cx
Copy link

Rel1cx commented Aug 11, 2019

const sleep = n => Atomics.wait(new Int32Array(new SharedArrayBuffer(4)), 0, 0, n * 1000)

@weixiaoxu123
Copy link

promise:
const sleep1 = (time)=>{ return new Promise((resolve)=>{ setTimeout(resolve, time) }) } sleep1(1000).then(()=>{ console.log(1) })
async/awiat:
const sleep1 = (time)=>{ return new Promise((resolve)=>{ setTimeout(resolve, time) }) } async function output(){ await sleep1(1000) console.log(1) } output()
generator:

`
function* gen(time) {
yield new Promise(function(resolve,reject){
setTimeout(resolve,time);
})
}
gen(1000).next().value.then(()=>{console.log(1)})
}

`

@daiyunchao
Copy link

什么是sleep? 什么实现用Promise 或是 async await的方法和setTimeout有本质上的区别吗? sleep不应该用代码的方式 阻塞住进程,让他啥也干不了吗?

function sleep(time){
	let currentTime=Date.now();
	while(Date.now()-currentTime<=time){
	}
	return;
}
console.log("aaa")
sleep(5000);
console.log("bbb")

@ahao430
Copy link

ahao430 commented Sep 10, 2019

看题目以为是实现类似于java的sleep

sleep(1000);
console.log('sleep之后做的事');

后来实在想不出来怎么实现,看了大家的答案,发现是我想多了,,确实没法实现这样的sleep

用while一直循环,直到时间到退出循环那个是真sleep啊

@rennma
Copy link

rennma commented Sep 22, 2019

const sleep = (time) => {
  return new Promise(resolve => setTimeout(resolve, time))
}

sleep(1000).then(() => {
    // 这里写你的骚操作
})

我为什么不直接settimeout呢,还要包一下

@hzjxiaojing
Copy link

123

@xhywxtt
Copy link

xhywxtt commented Nov 27, 2019

  1. 回调函数
function sleep(time, callback){
	if(typeof callback === "function"){
		setTimeout(callback, time);
	}
}
sleep(1000, function(){
	console.log("1");
})
  1. Promise
const sleep = time => {
	return new Promise(resolve => setTimeout(resolve, time));
}
sleep(1000).then(() => console.log("1"));
  1. Generator
function* sleepGenerator(time){
	yield new Promise(resolve => setTimeout(resolve, time));
}
const sleep = time => sleepGenerator(time).next().value;
sleep(1000).then(() => console.log("1"));
  1. await/async(做了改动)
async function sleep(time){
	await new Promise(resolve => {
		setTimeout(resolve, time);
	});
}
sleep(1000).then(() => console.log("1"));

async function sleep(time){
	await new Promise(resolve => {
		setTimeout(resolve, time);
	});
	console.log("1");
}
sleep(1000);

@ChenCong6837
Copy link

难道就不能不用定时器吗

function sleep (time) {
	var now = +Date.now()
	while (+Date.now() - now <= time) {}
	return
}
console.time(1)
sleep(2000)
console.log(123)
console.timeEnd(1)

console.time(1)
sleep(3000)
console.log(456)
console.timeEnd(1)
// 123
// 2000.244140625ms
// 456
// 3001.861328125ms

这种方式会阻塞代码的

@SnailOwO
Copy link

SnailOwO commented Jan 7, 2020

// Promise
function sleep(seconds) { return new Promise((resolve, reject) => { setTimeout(() => { resolve(); }, seconds); }) }

// generator
function* sleep(fn, seconds) { yield setTimeout(() => { fn.call(null); }, seconds); } sleep(demo,1000).next()

function demo() { console.log('233'); }

// async await
async function sleep(fn, seconds) { await setTimeout(() => { fn.call(null); }, seconds); } sleep(demo,1000)

不对之处,请指出一起讨论,谢谢

@lovelmh13
Copy link

setTimeout:

function con() {
	console.log(1);
}
function sleepForSettimeout(fn, delay) {
	setTimeout(() => {
		fn();
	}, delay);
}
sleepForSettimeout(con, 1000);

Promise:

function sleepForPromise(delay) {
	return new Promise(res => setTimeout(res, delay));
}
sleepForPromise(1000).then(con);

Generator:

function* sleepForGenerator(fn, delay) {
	yield setTimeout(() => {
		fn();
	}, delay);
}
var g = sleepForGenerator(con, 1000);
g.next();

Async/Await:

async function sleepForAsyncAwait(fn,delay) {
	await new Promise(res => setTimeout(res, delay));
	fn();
}
sleepForAsyncAwait(con ,1000);

@alt1o
Copy link

alt1o commented Feb 14, 2020

看题目以为是实现类似于java的sleep

sleep(1000);
console.log('sleep之后做的事');

后来实在想不出来怎么实现,看了大家的答案,发现是我想多了,,确实没法实现这样的sleep

是啊,这题出的就有问题,直接setTimeout不好嘛,为啥还要加这么多花里胡哨的

@a1029563229
Copy link

// Promise

function sleep1(time) {
  return new Promise(resolve => {
    setTimeout(() => {
      resolve();
    }, time);
  })
}

sleep1(1000).then(() => console.log("sleep1"));

// Generator

function* sleep2(time) {
  return yield sleep1(time);
}

const s = sleep2(1500);
s.next().value.then(() => console.log("sleep2"));


// Async/Await

async function sleep3(time) {
  await sleep1(time);
}

(async () => {
  await sleep3(2000);
  console.log("sleep3")
})()

@cutie6
Copy link

cutie6 commented Jun 27, 2020

1861593225237_ pic

@tjwyz
Copy link

tjwyz commented Jul 28, 2020

function sleep(ms) {
	return new Promise((resolve, reject)=>{
		setTimeout(()=>{
			resolve();
		}, ms)
	})
}
// promise
sleep(1000).then(()=>{
	console.log('1000ms after');
})

// async / await
async function main() {
	await sleep(1000);
	console.log('1000ms after');
}

// generator
function* main() {
	yield sleep(1000);
}
main().next().value.then(()=>{
	console.log('1000ms after');
})
// generator co
function co (generator) {
	const gen = generator();
	function cb (param) {
		let tmp = gen.next(param);
		if (tmp.done) return Promise.resolve(tmp.value);
		tmp.value.then((ret)=>{
			cb(ret)
		});
	}
	cb();
}
function* main() {
	yield sleep(1000);
	console.log('1000ms after');
	yield sleep(1000);
	console.log('2000ms after');
}
co(main);

@m7yue
Copy link

m7yue commented Sep 11, 2020

这道题其实就是异步逻辑同步化

// 回调
const sleep = (time, cb) => setTimeout(cb, time)
sleep(1000, () => console.log('开始搞事情~'))


// Promise
const sleep = (time) => {
  return new Promise((re, rj) => {
    setTimeout(re, time)
  })
}
sleep(1000).then(() => console.log('开始搞事情~'))


// Generator
const gen = function* (time) {
  console.log('开始搞事情~')
}
const sleep = (gen, time) => {
  let g = gen()
  setTimeout(() => g.next(), time)
}
sleep(gen, 1000)


// async/await
const sleep= async (time) => {
  await new Promise((re, rj) => {
    setTimeout(re, time)
  })
  console.log('开始搞事情~')
}
sleep(1000).then(() => console.log('或者这样搞事情~'))

@XuedaoYuan
Copy link

XuedaoYuan commented Sep 17, 2020

function sleep(interval) {
	return new Promise((resolve, reject) => {
		let timer
		const now = Date.now
		let startTime = now()
		let endTime = startTime
		const loop = () => {
			timer = window.requestAnimationFrame(loop)
			endTime = now()
			if (endTime - startTime >= interval) {
				window.cancelAnimationFrame(timer)
				resolve()
			}
		}
		timer = window.requestAnimationFrame(loop)
	})
}
sleep(2000).then(() => {
	// ...
	console.log('hello world!')
})

可能会比setTimeout精确一点点

@chris1299
Copy link

感觉是无法实现sleep。只能用while实现假的sleep

@DevinDon
Copy link

const sleep = delay => new Promise(resolve => setTimeout(resolve, delay));

@FujianLuan
Copy link

从语言设计上来说JS有了异步模型也就不需要Java 的那种sleep函数了。Java里面可以多线程并发,某一个线程可以sleep,这时会让出cpu资源;JS里面可以使用循环模拟sleep,但是sleep时间如果过长,cpu会一直占用着,造成卡死;另,setTimeout+promise系列还是属于异步逻辑,只是一层层的套壳。

@Unequaled804
Copy link

在9012年的今天,其他都是异端,请使用async/await。

pdd刚面试完个promise实现sleep,不能用async/await关键字

@Unequaled804
Copy link

//ES5
function sleep(callback,time) {
if(typeof callback === 'function')
setTimeout(callback,time)
}

function output(){
console.log(1);
}
sleep(output,1000);


参考:

* [Promise | 自个写一个Promise | Generator](https://blog.csdn.net/ImagineCode/article/details/81089107)

前几个方法都很棒,就这个ES5的咋感觉就是用setTimout实现了个setTimeout😂

@luke358
Copy link

luke358 commented Aug 18, 2022

异步具有传染性,sleep加上之后,使用的每个方法都要用async,或者then

@hzjxiaojing
Copy link

hzjxiaojing commented Aug 18, 2022 via email

@undeadfrost
Copy link

看到一篇文章分享一下 https://jasonformat.com/javascript-sleep/

@hzjxiaojing
Copy link

hzjxiaojing commented Oct 31, 2024 via email

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

No branches or pull requests