3

I have a boolean which is originally false. But in some future, if its value change (can change multiple times, but only to the same) will be true.

For example, with the given pseudocode

const hasChanged = false; // stateful

// This function can be called multipe times
const handleSubmit = () => {
   // ...
   hasChanged = true;
   // ...
}

I am always reassigning the value 'true' to my boolean... and I think that, maybe, it can be optimized by firstly checking if it is false, like this:

const handleSubmit = () => {
   // ...
   !hasChanged && hasChanged = true;
   // ...
}

But this will only be true if the conditional check (read + check) is faster than the write operation in JS, something that I don't know.

Any ideas?

Victor Molina
  • 2,353
  • 2
  • 19
  • 49
  • 2
    This feels like generally not something you should worry about at all, and as long as its not a getter/setter method you are not adding any additional overhead. The check, however, does add more overhead, definitely since JS is compiled JIT which means it needs to - technically - compile more code. Just assign the variable, as getting and checking from memory is probably the longer op. By a _teeeny meeny mini_ margin. So much that compromising the readability of your code is probably not worth it. – somethinghere Sep 19 '20 at 02:31

1 Answers1

10

Assigning the value unconditionally, without testing it first, will probably be a smidgen faster:

As a general rule of thumb, branches are slower than straight-line code (on all CPUs, and with all programming languages). -jmrk, V8 developer

This is the same line of reasoning behind the famous question: Why is processing a sorted array faster than processing an unsorted array?

That said, this is extremely unlikely to be a performance bottleneck. It's not worth worrying about.

The following micro-benchmark seems to bear this out, though micro-benchmarks are not all that reliable:

const len = 1e8;
const arr = Array.from({ length: len }, () => Math.random() < 0.5);
setTimeout(() => {
  // Wait for window to load completely and be free of CPU load
  const t0 = performance.now();
  for (let i = 0; i < len; i++) {
    if (!arr[i]) arr[i] = true;
  }
  console.log(performance.now() - t0);
}, 2000);
console.log('timeout set');

const len = 1e8;
const arr = Array.from({ length: len }, () => Math.random() < 0.5);
setTimeout(() => {
  // Wait for window to load completely and be free of CPU load
  const t0 = performance.now();
  for (let i = 0; i < len; i++) {
    arr[i] = true;
  }
  console.log(performance.now() - t0);
}, 2000);
console.log('timeout set');

On my machine, the conditional assignment takes 500ms or so on average, whereas the unconditional assignment takes 80ms or so on average.

CertainPerformance
  • 356,069
  • 52
  • 309
  • 320