具有复合赋值的JavaScript中的竞争条件 [英] Race condition in JavaScript with compound assignment

查看:67
本文介绍了具有复合赋值的JavaScript中的竞争条件的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我不是在谈论复杂的比赛条件涉及网络事件.相反,我似乎发现+=运算符在V8(Chrome 58或Node 8)中不是原子的.

I'm not talking about complex race conditions involving the network or events. Rather, I seem to have found out that the += operator is not atomic in V8 (Chrome 58, or Node 8).

下面的代码旨在并行运行两个所谓的线程.每个线程"重复调用一个函数,该函数在之后返回其number参数.睡觉那么多秒.结果是总结到蓄能器.

The code below aims to run two so-called threads in parallel. Each "thread" calls repeatedly a function that returns its number parameter after sleeping that many seconds. The results are summed up into an accumulator.

function sleep(ms) {
  return new Promise(resolve => setTimeout(resolve, ms));
}

// Return the passed number after sleeping that many seconds
async function n(c) {
  await sleep(c * 1000);
  console.log('End', c);
  return c;
}

let acc = 0;  // global

// Call n repeatedly and sum up results
async function nForever(c) {
  while (1) {
    console.log('Calling', c);
    acc += await n(c);  // += not atomic?!
    console.log('Acc', acc);
  }
}

(async function() {
  // parallel repeated calls
  nForever(1);
  nForever(5.3);  // .3 for sanity, to avoid overlap with 1 * 5
})();

问题在于,〜5秒后,我希望累加器为10.3(5乘以1 + 5.3乘以1).但是,它是5.3!

The problem is that after ~5 seconds, I'd expect the accumulator to be 10.3 (5 times 1 + 1 times 5.3). However, it's 5.3!

推荐答案

这不是竞争条件,因为您明确地使用await产生执行.

This is not a race condition, because you are explicitly yielding the execution using await.

该标准定义诸如+=之类的复合赋值不是原子的:复合赋值的左侧在右侧之前进行评估. [

The standard defines that a compound assignment such as += is not atomic: The left-hand-side of a compound assignment is evaluated before the right-hand-side.[1]

因此,如果您的RHS以某种方式更改acc,则更改将被覆盖.最简单的例子:

So if your RHS changes acc somehow, the changes will be overwritten. Most simple example:

var n = 1;
n += (function () {
    n = 2;
    return 0;
})();

console.log(n);

这篇关于具有复合赋值的JavaScript中的竞争条件的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆