public int tobinary(int x)
{
int count = 0;
while(x!=0)
{
x=(x&(x<<1)); //how this stuff is working
count++;
}
return count;
}
上面的代码工作正常,但是实际上我确实复制并粘贴了。所以我只想知道上面提到的那行代码是如何工作的。这对我有很大的帮助。
例如,我给i / p作为7的二进制格式是0111,所以我们的答案将是3,但是怎么办?
答案 0 :(得分:4)
我们知道,<<
运算符将其操作数的所有位向左移动,这里向左移动1。此外,&
运算符对两个操作数的所有位进行按位运算。
x
何时不为0
?当按位与运算找到两个在两个操作数中都设置的位时。只有1
和x
中有2个或更多连续的x << 1
位时,这种情况才会成立。
x : 0000 0111
x << 1: 0000 1110
-----------------
&: 0000 0110
count = 1
如果不是0
,则该数字中至少有2个连续的1
位,并且该数字中连续的1
位的(最大)数量已减少了1.因为我们首先进入循环,所以请数一数再试一次。最终将不再有连续的1
位,因此我们以正确的计数退出循环。
x : 0000 0110
x << 1: 0000 1100
-----------------
&: 0000 0100
count = 2
x : 0000 0100
x << 1: 0000 1000
-----------------
&: 0000 0000
count = 3, exit loop and return.
答案 1 :(得分:1)
x = (x & (x << 1))
执行足够的时间以消除1
位的最长连续组。每次循环迭代都会将1
的每个连续组减少一个,因为在逻辑上AND
本身已向左移一位。这一直持续到没有连续的1
组为止。
为数字110111101
进行说明:
110111101 // initial x, longest sequence 4
1101111010 // x << 1, count 1
100111000 // new x, longest sequence 3
1001110000 // x << 1, count 2
110000 // new x, longest sequence 2
1100000 // x << 1, count 3
100000 // new x, longest sequence 1
1000000 // x << 1, count 4
0 // new x, end of loop
请注意,从Java 7开始,使用int input = 0b110111101
声明二进制文字很方便。
答案 2 :(得分:0)
<<(左移):二进制左移运算符。左操作数的值向左移动右操作数指定的位数。
即x<<1
将值位从右向左移动1,然后在单位位置添加0
。因此,假设x=7
的位表示形式为111
。执行x << 1
将返回110
,即丢弃head元素,将这些位左移并最后添加0
。
对于x=7
的初始值,可以将此while循环分解为以下迭代:
迭代1)111 & 110 =110
迭代2)110 & 100 =100
迭代3)100 & 000 =000
由于x
的值为0,因此不再进行迭代
希望这说明了此代码的行为。您可以自己输入System.out.println(Integer.toBinaryString(x));
来查看x
的位值变化
答案 3 :(得分:0)
那么,对于while循环中的每个迭代,发生了什么 x = x(AND运算符)(2 * x)。
例如,当x = 7时 计数= 0
Iteration 1:
//x = 7 & 14 which results in 6 ie
0111
1110 (AND)
-------
0110 => 6
-------
count = 1
Iteration 2:
//x = 6 & 12 results in 4
0110
1100 AND
-------
0100 => 4
-------
count = 2
Iteration 3:
// x = 4 & 8 results in 0
0100
1000 AND
-----
0000
-----
count = 3
这就是您7换3的方式