xgqfrms™, xgqfrms® : xgqfrms's offical website of cnblogs! xgqfrms™, xgqfrms® : xgqfrms's offical website of GitHub!

How to use JavaScript to implement precise setTimeout and setInterval All In One

How to use JavaScript to implement precise setTimeout and setInterval All In One

如何使用 JavaScript 实现精确的 setTimeout 和 setInterval

setTimeoutPreciseSimulator & setIntervalPreciseSimulator

"use strict";

/**
 *
 * @author xgqfrms
 * @license MIT
 * @copyright xgqfrms
 * @created 2020-07-0
 * @modified
 *
 * @description 使用 JavaScript 实现精确的 setTimeout 和 setInterval
 * @difficulty Easy Medium Hard
 * @complexity O(n)
 * @augments
 * @example
 * @link
 * @solutions
 *
 */

const log = console.log;

// 同步: 使用 js 实现精确的 setTimeout
function setTimeoutPreciseSimulator(callback, time = 0) {
  const begin = new Date().getTime();
  while (true) {
    const end = new Date().getTime();
    if(end - begin >= time) {
      log(`end - begin`, end - begin);
      callback();
      break;
    }
  }
}

// 同步: 使用 js 实现精确的 setInterval
function setIntervalPreciseSimulator(callback, time = 0, count = 10) {
  function interval(callback, time) {
    const begin = new Date().getTime();
    while (true) {
      const end = new Date().getTime();
      if(end - begin >= time) {
        log(`end - begin`, end - begin);
        callback();
        break;
      }
    }
    if(count) {
      log(`\ncount =`, count);
      count--;
      interval(callback, time);
    }
  }
  // init
  interval(callback, time);
}


// setTimeoutPreciseSimulator(() => console.log(`OK 1000`), 1000)
// end - begin 1000
// OK 1000

setIntervalPreciseSimulator(() => console.log(`OK 1000`), 1000)

// end - begin 1000
// OK 1000

// count = 10
// end - begin 1000
// OK 1000

// count = 9
// end - begin 1000
// OK 1000

// count = 8
// end - begin 1000
// OK 1000

// count = 7
// end - begin 1000
// OK 1000

// count = 6
// end - begin 1000
// OK 1000

// count = 5
// end - begin 1000
// OK 1000

// count = 4
// end - begin 1000
// OK 1000

// count = 3
// end - begin 1000
// OK 1000

// count = 2
// end - begin 1000
// OK 1000

// count = 1
// end - begin 1000
// OK 1000

requestAnimationFrame bug

requestAnimationFrame bug ? can not pass params

// 🐞🐛bug ? can not pass params

function requestAnimationFramePreciseSimulator(callback, time = 0, count = 10) {
  // function interval(callback, time) {
  function interval() {
    const begin = new Date().getTime();
    while (true) {
      const end = new Date().getTime();
      if(end - begin >= time) {
        log(`end - begin`, end - begin);
        callback();
        break;
      }
    }
    if(count) {
      log(`\ncount =`, count);
      count--;
      requestAnimationFrame(interval);
      // window.requestAnimationFrame(interval);
    }
  }
  // init
  requestAnimationFrame(interval);
  // window.requestAnimationFrame(interval);
  // ReferenceError: requestAnimationFrame is not defined
}

// requestAnimationFramePreciseSimulator(() => console.log(`OK 1000`), 1000)

🐞


window.requestAnimationFrame(callback);

// pass 参数???

window.requestAnimationFrame(callback(args));

window.requestAnimationFrame(callback, args);

https://developer.mozilla.org/en-US/docs/Web/API/Window/requestAnimationFrame

https://caniuse.com/#feat=requestanimationframe

requestAnimationFrame

function repeatOften() {
  // do whatever
  requestAnimationFrame(repeatOften);
}
requestAnimationFrame(repeatOften);

https://css-tricks.com/using-requestanimationframe/

js 实现 每间隔一秒,打印一个数组元素

简单 js 基础面试题


// js 实现 每间隔一秒,打印一个数组元素

let arr = [1,2,3];
let i = 0;
let timer = setInterval(() => {
  console.log(arr[i++]);
  if(arr.length === i) {
    clearInterval(timer);
  }
}, 1000);


// function es5Func (arr) {
//   // var hoisting bug
//   for (var i = 0; i < arr.length; i++) {
//     setTimeout(function (){
//       console.log('item, i =', arr[i], i);
//     }, (i + 1) * 1000);
//   }
// }
// es5Func([1, 2, 3]);

function es5Func (arr) {
  // var hoisting bug
  for (var i = 0; i < arr.length; i++) {
    // closure & IIFE
    (function(i) {
      setTimeout(function (){
        console.log('item, i =', arr[i], i);
      }, (i + 1) * 1000);
    })(i);
  }
}
es5Func([1, 2, 3]);


// const es6Func = (arr = []) => {
//   for (let [i, item] of arr.entries()) {
//     setTimeout(() => {
//       console.log('i, item =', i, item);
//     }, (i + 1) * 1000);
//   }
// }
// es6Func([1, 2, 3]);



const es6Func = (arr = []) => {
  for (let item of arr) {
    setTimeout(() => {
      console.log('item =', item);
    }, (arr.indexOf(item) + 1) * 1000);
    // setTimeout(() => {
    //   console.log('item =', item);
    // }, item * 1000);
  }
}
es6Func([1, 2, 3]);


refs

https://www.cnblogs.com/xgqfrms/p/11399442.html

https://javascript.info/settimeout-setinterval

https://stackoverflow.com/questions/29971898/how-to-create-an-accurate-timer-in-javascript



©xgqfrms 2012-2020

www.cnblogs.com/xgqfrms 发布文章使用:只允许注册用户才可以访问!

原创文章,版权所有©️xgqfrms, 禁止转载 🈲️,侵权必究⚠️!


posted @ 2020-07-29 17:00  xgqfrms  阅读(270)  评论(2编辑  收藏  举报