int isPower2(int x) {
int neg_one = ~0;
return !(neg_one ^ (~x+1));
}
这段代码有效,我已经实现了它并且表现完美。但是,我无法理解为什么。当我手工完成时,它对我没有任何意义。
假设我们以4位数字开头,4:
0100
这显然是2的幂。但是当我遵循算法时,~x + 1 =
1011 + 1 = 1100
对负数(1111)进行异或运算得到0011.!(0011)= 0.我在哪里错了?我知道这必须是我手工做的方式的一个缺陷。
答案 0 :(得分:0)
用Inigo Montoya的话来说,“我认为这不符合你的想法。”
让我们把它分解。
这会翻转'x'的位,然后加一。这与采用'x'的2的补码相同。或者,换句话说,这与'-x'相同。
使用我们在步骤1中提到的内容,这简化为......
neg_one ^ (-x)
或更简单......
-1 ^ (-x)
但是等等!对-1进行XOR'ing与翻转位相同。那是......
~(-x)
如果我们使用2的补码,这可以更简化。
~(-x) + 0
= ~(-x) + 1 - 1
= x - 1
如果您正在寻找一种简单的方法来确定数字是否为2的幂,则可以使用以下代码来代替大于零的数字。如果它是2的幂,它将返回true。
(x & (x - 1)) == 0