(b&amp;(1&lt; <i))vs =“”((b =“”>&gt; i)&amp; 1)C ++

时间:2018-04-30 04:39:01

标签: c++ performance bit-manipulation bit

通常需要将数据类型表示为位序列,并在整个长度的循环内获取它们。虽然我发现((b >> i) & 1)更直观,但最近我看到一本书使用了(b&(1<<i))。他们中的任何一个是更有利还是更有效,如果其中一个是,为什么?

2 个答案:

答案 0 :(得分:3)

假设您使用它来测试一点(因此结果的差异是无关紧要的),它取决于上下文以及编译器对它做什么以及其他因素。

例如,当使用GCC 7.3为现代x86编译时,它们是exactly the same,两者都可以编译为这个序列:

sarx eax, edi, esi
and eax, 1

当使用结果实际做出决定(而不是实现布尔值)时,代码仍然是相同的。显然,如果代码是相同的,效率就没有差别。 Clang喜欢使用btsetc(或在适当时使用cmov或控制流中的标志),但对两个片段也做同样的事情。 MSVC确实以不同的方式编译片段,并且在某种意义上可能“更喜欢”1 << i公式。

实现b & (1 << i) 字面上(我没有观察到任何编译器实际上做过)需要额外的指令将常量1加载到寄存器中,尽管这并不一定意味着需要额外的时间(尽管可以):创建1独立于其他所有内容,因此它可以在其他所有内容之前执行,然后移位独立于b,因此它可以在i准备就绪后执行但在b之前。

答案 1 :(得分:2)

哪个更有利?

取决于您需要的数据。

((b >> i) & 1) gives you a 1 or 0.

(b & (1 << i)) gives you a 0 or 2^i.

哪个更有效?

效率差异在他们之间可以忽略不计。另外,不同的架构和代码编译的区别也不同。