JS中setTimeout和setInterval的最大延时值详解


Posted in Javascript onFebruary 13, 2017

前言

JavaScript提供定时执行代码的功能,叫做定时器(timer),主要由setTimeout()setInterval()这两个函数来完成。而这篇文中主要给大家介绍的是关于JS中setTimeout和setInterval最大延时值的相关问题,需要的朋友们下面来一起学习学习吧。

先来看这样一段代码:

function update() {
 loadData().then(function(data) {
  $('#content').html(data.content);
  var delay = data.nextUpdateTime - new Date();
  if (delay > 0) {
   setTimeout(update, delay);
  }
 });
}

其流程非常简单:通过AJAX加载数据后更新HTML的内容;如果有指定下次更新时间,则通过计时器在该时间点再执行一次整个流程。

要说这段代码有什么隐患的话,那就是data.nextUpdateTime与当前时间的时间差(即delay变量的值)比较小的时候,会导致内容频繁更新。但这是属于正常的业务逻辑,要优化就只能牺牲内容更新的即时性。然而这里我要说的是,当时间差非常大的时候,也会出现同样的问题。

下面模拟一下这个场景:

function log() {
 console.log('executed');
}

var nextUpdateTime = new Date();
// 设为一个月后
nextUpdateTime.setMonth(nextUpdateTime.getMonth() + 1);

var delay = nextUpdateTime - new Date();
setTimeout(log, delay);

这段代码的原意是让log函数在一个月后执行,但是运行一下就可以发现,该函数会马上执行。为什么会这样呢?

搜一下相关内容可以发现,setTimeout是使用Int32来存储延时参数值的,也就是说最大的延时值是2^31-1。一旦超过了最大值,其效果就跟延时值为0的情况一样,也就是马上执行。

这个最大的延时值已经接近一个月了,一般情况下,用户也不会长时间开着一个网页,如果真开了这么久,那就刷新一下吧:

function update() {
 loadData().then(function(data) {
  $('#content').html(data.content);
  var delay = data.nextUpdateTime - new Date();
  if (delay > 0) {
   // 限制最大延时值为一天
   var ONE_DAY = 24 * 60 * 60 * 1000;
   if (delay > ONE_DAY) {
    setTimeout(function() {
     window.location.reload();
    }, ONE_DAY);
   } else {
    setTimeout(update, delay);
   }
  }
 });
}

同样的问题也存在于setInterval中。这也算是Javascript中一个比较隐蔽的坑了。

总结

以上就是这篇文章的全部内容了,希望本文的内容对大家的学习或者工作能带来一定的帮助,如果有疑问大家可以留言交流。

Javascript 相关文章推荐
js全选按钮的实现方法
Nov 17 Javascript
Jquery技巧(必须掌握)
Mar 16 Javascript
深入浅析JavaScript中的scrollTop
Jul 11 Javascript
关于JavaScript 原型链的一点个人理解
Jul 31 Javascript
JavaScript仿聊天室聊天记录
Dec 27 Javascript
Web纯前端“旭日图”实现元素周期表
Mar 10 Javascript
React-Native实现ListView组件之上拉刷新实例(iOS和Android通用)
Jul 11 Javascript
让webpack+vue-cil项目不再自动打开浏览器的方法
Sep 27 Javascript
详解webpack loader和plugin编写
Oct 12 Javascript
Vue+Element实现动态生成新表单并添加验证功能
May 23 Javascript
JS实现的简单tab切换功能完整示例
Jun 20 Javascript
vue遍历生成的输入框 绑定及修改值示例
Oct 30 Javascript
Vue.js实现简单动态数据处理
Feb 13 #Javascript
JavaScript获取select中text值的方法
Feb 13 #Javascript
详谈$.data()的用法和作用
Feb 13 #Javascript
基于Angularjs+mybatis实现二级评论系统(仿简书)
Feb 13 #Javascript
JavaScript实现公历转农历功能示例
Feb 13 #Javascript
JS判断键盘是否按的回车键并触发指定按钮点击操作的方法
Feb 13 #Javascript
jQuery源码分析之sizzle选择器详解
Feb 13 #Javascript
You might like
相对路径转化成绝对路径
2007/04/10 PHP
在PHP中PDO解决中文乱码问题的一些补充
2010/09/06 PHP
php preg_replace替换实例讲解
2013/11/04 PHP
php中文验证码实现示例分享
2014/01/12 PHP
用正则xmlHttp实现的偷(转)
2007/01/22 Javascript
js弹出框轻量级插件jquery.boxy使用介绍
2013/01/15 Javascript
node.js中的fs.lstatSync方法使用说明
2014/12/16 Javascript
Jquery 实现图片轮换
2015/01/28 Javascript
深入理解JavaScript系列(46):代码复用模式(推荐篇)详解
2015/03/04 Javascript
喜大普奔!jQuery发布 3.0 最终版
2016/06/12 Javascript
浅析Node.js:DNS模块的使用
2016/11/23 Javascript
利用JS判断字符串是否含有数字与特殊字符的方法小结
2016/11/25 Javascript
基于Vue实现timepicker
2017/04/25 Javascript
JS遍历DOM文档树的方法实例详解
2018/04/03 Javascript
layui富文本编辑器前端无法取值的解决方法
2019/09/18 Javascript
[17:00]DOTA2 HEROS教学视频教你分分钟做大人-帕克
2014/06/10 DOTA
[41:20]2014 DOTA2华西杯精英邀请赛 5 24 NewBee VS DK
2014/05/26 DOTA
Python处理RSS、ATOM模块FEEDPARSER介绍
2015/02/18 Python
Python读取mp3中ID3信息的方法
2015/03/05 Python
python开发之list操作实例分析
2016/02/22 Python
windows及linux环境下永久修改pip镜像源的方法
2016/11/28 Python
Python脚本实现自动将数据库备份到 Dropbox
2017/02/06 Python
Python基于多线程实现ping扫描功能示例
2018/07/23 Python
对python条件表达式的四种实现方法小结
2019/01/30 Python
Python存储读取HDF5文件代码解析
2020/11/25 Python
CSS3区域模块region相关编写示例
2015/08/28 HTML / CSS
CSS3中设置3D变形的transform-style属性详解
2016/05/23 HTML / CSS
Parts Express:音频、视频和扬声器的第一来源
2017/04/25 全球购物
2013年入党人员的自我鉴定
2013/10/25 职场文书
网络研修随笔感言
2014/02/17 职场文书
职业培训师职业生涯规划
2014/02/18 职场文书
工厂见习报告范文
2014/10/31 职场文书
毕业班班主任工作总结2015
2015/07/23 职场文书
创业计划书之外语培训班
2019/11/02 职场文书
2019幼儿园感恩节活动策划书
2019/11/28 职场文书
Vertica集成Apache Hudi重磅使用指南
2022/03/31 Servers