An expensive jump with GCC 5.4.0
<p>I had a function which looked like this (showing only the important part):</p>
<pre><code>double CompareShifted(const std::vector&lt;uint16_t&gt;&amp; l, const std::vector&lt;uint16_t&gt; &amp;curr, int shift, int shiftY)  {
...
  for(std::size_t i=std::max(0,-shift);i&lt;max;i++) {
     if ((curr[i] &lt; 479) &amp;&amp; (l[i + shift] &lt; 479)) {
       nontopOverlap++;
     }
     ...
  }
...
}
</code></pre>
<p>Written like this, the function took ~34ms on my machine. After changing the condition to bool multiplication (making the code look like this):</p>
<pre><code>double CompareShifted(const std::vector&lt;uint16_t&gt;&amp; l, const std::vector&lt;uint16_t&gt; &amp;curr, int shift, int shiftY)  {
...
  for(std::size_t i=std::max(0,-shift);i&lt;max;i++) {
     if ((curr[i] &lt; 479) * (l[i + shift] &lt; 479)) {
       nontopOverlap++;
     }
     ...
  }
...
}
</code></pre>
<p>the execution time decreased to ~19ms.</p>
<p>The compiler used was GCC 5.4.0 with <code>-O3</code> and after checking <a href="https://godbolt.org/g/5lKPF3" rel="nofollow noreferrer">the generated asm code using godbolt.org</a> I found out that the first example generates a jump, while the second one does not. I decided to try GCC 6.2.0 which also generates a jump instruction when using the first example, but GCC 7 seems to not generate one anymore.</p>
<p>Finding out this way to speed up the code was rather gruesome and took quite some time. Why does the compiler behave this way? Is it intended and is it something the programmers should look out for? Are there any more things similar to this?</p>