程序一:编写一个函数getbits(x,p,n),它将返回x中从右边数第p位开始向右边n位的字段,这里假定右边第一位是第0位,n和 p都是合理的正值
先看程序:(先把指定为移到最右边,然后再与1与,即取出来即可)
unsigned getbits(unsigned x, int p, int n)
{
return (x >> (p+1-n)) & ~( ~0 << n);
}
问题一:什么叫n和p都为合理的正值
答:即:p首先得在 unsigned 的范围内p+1-n>=0;
问题二:unsigned是什么类型
答:点击打开链接
程序二:编写一个函数setbits(x,p,n,y),该函数返回对x执行下列操作后的结果值:将x中从第p位开始的n个(二进制)位设置为y中最右边n位的值,x中的其余各位保持不变
解释:先看后部分吧,后面的就是先取出y的最右边n位值,然后移动到p~(p+1-n)这个范围来,取出来的值,除了这个范围是与 y之前的相同外,其他的都是 0.
前面的就是把p~(p+1-n)这个范围都变为0就好,其他位不变,具体操作方法看程序就好,个人觉得这个每个人变换的方法不同。
unsigned setbits(unsigned x, int p, int n, unsigned y)
{
return (x & ((~0 << (p + 1)) | (~(~0 << (p + 1 - n))))) | ((y & ~(~0 << n)) << (p + 1 - n));
}
int main(void)
{
unsigned i;
unsigned j;
unsigned k;
int p;
int n;
for(i = 0; i < 30000; i += 511)
{
for(j = 0; j < 1000; j += 37)
{
for(p = 0; p < 16; p++)
{
for(n = 1; n <= p + 1; n++)
{
k = setbits(i, p, n, j);
printf("setbits(%u, %d, %d, %u) = %u\n", i, p, n, j, k);
}
}
}
}
return 0;
}
问题一:测试程序有些奇怪
答:的确是,哈哈,我也不知道为啥。
程序三:编写一个函数invert(x,p,n),该函数返回对x执行下列操作后的结果值:将x中从第p为开始的n个(二进制)为求反(即,1变0,0变成1),x的其余各位保持不变。
思路:把需要改变的那部分与 1异或即可。
unsigned invert(unsigned x, int p, int n)
{
return x ^ (~(~0U << n) << p);
}
#include <stdio.h>
int main(void)
{
unsigned x;
int p, n;
for(x = 0; x < 700; x += 49)
for(n = 1; n < 8; n++)
for(p = 1; p < 8; p++)
printf("%u, %d, %d: %u\n", x, n, p, invert(x, n, p));
return 0;
}