JavaScript:使用异步事件回调的线程安全性? (我需要'易变'还是什么?)

时间:2015-09-14 21:58:53

标签: javascript multithreading asynchronous callback volatile

假设我有以下代码来预加载2张图片,并且仅在加载两个图片后执行某些操作:

var numLoaded = 0;

function OnImageLoaded()
{
  numLoaded++;
  if (numLoaded==2) alert("Got 'em!");
}

var a = new Image();
var b = new Image();
a.onload = OnImageLoaded;
b.onload = OnImageLoaded;
a.src = 'foo.jpg';
b.src = 'bar.jpg';

分配a.srcb.src会导致两张图片都在后台加载,OnImageLoaded()被调用,然后就可以了。

显然if (numLoaded==2)之后的代码应该只运行一次。

现在,是否有可能发生这种情况:

  1. 加载第一张图片,调用该函数,numLoaded++将计数器增加到一张
  2. 加载第二个图像,调用该函数(在不同的线程中),numLoaded++将计数器增加到两个
  3. 第一个线程检查numLoaded==2现在是真的,所以代码被执行,
  4. 第二个帖子也检查numLoaded==2哪个仍然是真的,所以假定再运行的代码再次执行 ←问题!
  5. 这是一个机会(虽然非常小),我该如何避免这种情况?在其他语言中,我会使用一个关键部分,或者使用互斥体,或者使用numLoaded volatile并执行n=(++numLoaded)或者其他什么,但是我如何在JS中使用它?

1 个答案:

答案 0 :(得分:3)

正常情况下的Javascript does not run concurrently。有一些方法可以使用Node.js这样做,但它相当困难,而不是你需要担心的典型情况。