setInterval函数线程在Jquery中与其他setInterval函数一起被延迟

时间:2016-04-19 13:38:07

标签: jquery asp.net-mvc

我在javascript中有两个时间间隔变量,执行时间为1秒,为5秒。我在myTimer1()睡觉。在那种情况下,当前时间函数myTimer()显示在浏览器上显示时间的延迟。实际上它跳得很快。我希望连续第二次显示实时。如果有任何其他方式来显示实时,我们非常感激。 我在基于MVC的Web应用程序中面临这种情况。

<!DOCTYPE html>
<html>
<body>

<p>A script on this page starts this clock:</p>
<p id="demo"></p>
<p id="demo1"></p>
<script>
var myVar = setInterval(function(){ myTimer() }, 1000);

function myTimer() {
    var d = new Date();
    var t = d.toLocaleTimeString();
    document.getElementById("demo").innerHTML = t;
}

var myVar1 = setInterval(function(){ myTimer1() }, 5000);

function myTimer1() { 
document.getElementById("demo1").innerHTML = "Prashant";
//Calling some function from server side which taking some time to calculated data to showing on browser and it will take some time to load like 2-3 sec. so I use sleep for example.
sleep(3000);
}

function sleep(milliseconds) {
  var start = new Date().getTime();
  for (var i = 0; i < 1e7; i++) {
    if ((new Date().getTime() - start) > milliseconds){
      break;
    }
  }
}

</script>

</body>
</html>

2 个答案:

答案 0 :(得分:2)

您是否考虑过完全删除sleep()来电?这样的调用通常会导致令人难以置信的糟糕性能和意外结果(因为它会占用你的UI线程):

function myTimer1() { 
    document.getElementById("demo1").innerHTML = "Prashant";
    // This is going to clog up your UI thread and prevent anything from occurring
    // sleep(3000);
}

尝试删除它,你会看到你的计时器连续运行。如果仍然需要引起某种类型的延迟,只需使用setTimeout()函数来处理(并停止当前的计时器)。

没有sleep()

的示例

<!DOCTYPE html>
<html>
<body>

<p>A script on this page starts this clock:</p>
<p id="demo"></p>
<p id="demo1"></p>
<script>
var myVar = setInterval(function(){ myTimer() }, 1000);

function myTimer() {
    var d = new Date();
    var t = d.toLocaleTimeString();
    document.getElementById("demo").innerHTML = t;
}

var myVar1 = setInterval(function(){ myTimer1() }, 5000);

function myTimer1() { 
document.getElementById("demo1").innerHTML = "Prashant";

}

function sleep(milliseconds) {
  var start = new Date().getTime();
  for (var i = 0; i < 1e7; i++) {
    if ((new Date().getTime() - start) > milliseconds){
      break;
    }
  }
}

</script>

</body>
</html>

关于您的数据库评论

如果要从数据库中提取用户,则应该在完成时让大概的AJAX调用处理掉。如果你想每5秒吸一个新用户,你可以考虑使用这样的appraoch:

 // Keep track of how many users you have pulled
 var usersPulled = 0;

 // Every 5 seconds, pull a user
 var userTimer = setTimeout(function(){ pullUser(); }, 5000);

 function pullUser(){
      // Make an AJAX call to pull your specific user
      $.get('/Users/Get', { skip: usersPulled++ }, function(user){
          if(user)
          {
             // Get the user that was pulled and output them
             $('#userlist').append('<p>' + user + '</p>');
          }
          else
          {
             // No user was found, stop your timer
             clearTimeout(userTimer);
          }
     });
}

然后您的服务器端代码可能类似于以下内容来拉动数据库中的“下一个”用户:

public string Get(int skip)
{
      // Get the first user available
      var user = _context.Users.OrderBy(u => u.Name).Skip(skip).FirstOrDefault();
      if(user != null)
      {
            return user.Name;
      }
      return null;
}

答案 1 :(得分:1)

浏览器上只有一个主要的JavaScript JavaScript线程,它适用于事件队列(作业队列)系统。当您通过setTimeoutsetInterval计划计时器时,当达到应该调用回调的时间时,实际发生的是作业(事件)排队等待主UI线程处理什么时候可以。

你的sleep函数占用主UI线程,所以除了在while循环中旋转之外它无法做任何事情。这包括无法处理来自计时器的回调。

只需删除sleep即可。它没有做任何有用的事情。它 un 有用的东西。

如果由于某种原因,您希望在致电timer1三秒后执行某些操作,则可以使用setTimeout执行此操作:

function myTimer1() { 
    document.getElementById("demo1").innerHTML = "Prashant";
    setTimeout(function() {
        // Do the thing you wanted to do 3 seconds later
    }, 3000);
}

你在评论中说过:

  

基本上我只是把睡眠作为例子。数据来自sql连接,需要一些时间。

嗯,用我们看不到的代码来帮助你真的很难。

通常,您将通过ajax查询该数据,因此它将是异步的(如上面的setTimeout),并且不会锁定浏览器,除非您告诉它是同步的(提示:don不要这样做,使用回调。)