关于C语言的位运算的问题

来源:百度知道 编辑:UC知道 时间:2024/05/01 11:57:12
C语言课本上讲的第一个例题:取一个整数a从右端开始的4-7位。
main()
{ unsigned a,b,c,d;
b=a>>4;
c=~(~0<<4);
d=b&c;
printf("%o,%d\n%o,%d\n",a,a,d,d);
}
运行情况如下:
输入331;
输出的是 331,217
15,13
然后它课本上总结的是说:可以任意指定从右面第m位开始取其右面的n位,只要将程序中的"b=a>>4"改成"b=a>>(m-n+1)"
我不明白这句话的意思,就象上面的程序, 取右端开始的4-7位,用这个公式b=a>>(m-n+1),是不是等于b=a>>(7-4+1)=a>>4; 如果取5-7位的话,b=a>>(7-5+1)=a>>3;取5-7位应该是向右移4个位吧?它这个b=a>>(m-n+1)公式的m和n代表什么啊?

第2个程序:
循环位移,
main()
{ unsigned a,b,c;
int n;
scanf("a=%do,n=%d"&a,&n);
b=a<<(16-n);
c=a>>n;
c=c|b;
printf("%o\n%o",a,c);
}
这个程序课本上的数太大了,请你们帮我输入一个数举例说明一下就可以;
不懂的地方是:这个地方没有用循环之类的语句,它为什么是循环移位?
还有就是举例解释一下什么是补码和反码啊?不会啊。。。

谢谢啦。。。

第一题:
如果书本上真是那个意思,那就是它的错误。
这个程序关键的是这几行代码:
b=a>>3; //你写的是4,估计是抄错了,应该是3,代表向右移3位。这样从右数第4位就变成了右数第一位了
c=~(~0<<4); //这个才是关键,~0表示各个位都是1,再向左移4位,此时低4位是0,其他位是1,再取反以后,c的二进制数低4位是1,其他位是0
d=b&c; //b和c按位与,因为c的低4位是1,其他位是0,1&任何数=任何数,0&任何数=0.所以取到的就是b的低4位了。 也就是a的4-7位。
如果按照书本上归纳:从右面开始取m—n位,代码如下:
b=a>>(m-1);
c=~(~0<<(n-m));
d=b&c;
第二题:
这个程序的功能其实就是将一个数的二进制位中的低n位,移动到它的高n位,相应的,原来的高16-n位也就变成了低16-n位了。这个就是它所谓的“循环移位”。
举个例子:
a的二进制数:0110 1100 0011 1010
取n为4,则
b=a<<12; //b=1010 0000 0000 0000 只保留了a的低4位
c=a>>4; //c=0000 0110 1100 0011 低4位丢失,高4位补0
c=c|b; //此时按位或,c=1010 0110 1100 0011 实现了低4变成了高4位
明白了吧?
举例说明补码和反码:
反码好理解,就是取反,比如0110的反码是1001.
补码要分类。正数的补码就是他的原码。负数的补码遵循规则"绝对值按位取反再+1"
下面举例子:
8的补码: 8的原码:0000 1000。补码仍然是0000 1000
-8的补码:因为是负数,最高位为1,需要保留。而-8的绝对值如上,合在一起就是1000 1000.先按位取反:1111 0111,再+1: 1111 1000。这个就是-8的补码了。

做移几位和右移几位是C语言里面规定的,并不需要循环,