0

我是桌面应用背景,在学习Javascript的时候,真的很难理解Javascript中的线程机制。

例如:

<!DOCTYPE HTML>
<html>
<head>
<script src="http://ajax.googleapis.com/ajax/libs/jquery/1.9.1/jquery.min.js"></script>
<script>
$(document).ready(function(){
    $("#btn1").click(function(){
        for (var i = 0 ; i < 100000 ; i ++){
            $("#loop1").html(i);

        }
    });

    $("#btn2").click(function(){
        for (var i = 0 ; i < 100000 ; i ++){
            $("#loop2").html(i);

        }
    });
});
</script>
</head>
<body>

Loop 1 : <p id="loop1"></p>
<button id="btn1">Button 1</button>
<br/><br/><br/>

Loop 2 : <p id="loop2"></p>
<button id="btn2">Button 2</button>

</body>
</html>

当我单击按钮 1 时,浏览器会挂起,因此当我单击按钮 2 时,它不会响应。通常在桌面应用程序中,我会将循环发布到后台线程中。但是我将如何在 Javascript 中做到这一点?或者在Javascript中处理长时间处理的最佳方法是什么?


编辑:

下面的代码不起作用,但不知道为什么。

$("#btn1").click(function(){

        setTimeout( function(){
            for (var i = 0 ; i < 100000 ; i ++){
                $("#loop1").html(i);

            }
        }
        , 0);
    });
4

3 回答 3

2

Javascript 中没有原生的多线程。

一些技术尝试在 HTML5 规范 ( WebWorkers ) 中实现多线程,其他技术尝试在 javascript 本身中实现它,但基本规范 (ECMA) 是单线程的。

你可以在谷歌上搜索..

于 2013-04-05T08:05:59.770 回答
2

正如之前的答案已经说明的那样,WebWorkers是 Javascript 的multi-threading的唯一选择。不幸的是,如果您想进行 DOM 修改,就没有希望了。

大多数人忘记的是,当您调用函数时setTimeoutsetInterval UI 不会冻结并且仍会接收更新

function btnClickHandler() {
    setTimeout(doStuff, 1); // prevent UI freeze
}

function doStuff() {
    // do your stuff here
}

在你的情况下:

var i, interval;

$("#btn1").click(function(){
    i = 0; // reset i

    // create interval
    interval = setInterval(btn1Handler, 1); // run btn1Handler every 1ms
});

function btn1Handler() {
    $("#loop1").html(i);

    if(i++ >= 100000) {
        // cancel the interval
        clearInterval(interval);
    }
}
于 2013-04-05T08:09:36.923 回答
0

除了如果您使用网络工作者(并且他们不能直接更改 DOM),您的浏览器中只有一个用户 javascript 线程。

事件被堆叠,直到您的函数返回。您可以有两个长时间运行的操作并行更改 DOM。

于 2013-04-05T08:06:28.960 回答