在一定的取值范围内,将一个整数左移1位相当于乘以2;右移一位相当于对2取整。例如:
100 = 0110 0100b
100 >> 1 = 0011 0010b
0011 0010b = 50
100 << 1 = 1100 1000b
1100 1000b = 200
操作数为无符号数时,右移时高位补0,左移时低位补0;
如果是正数,那么高位移入0;
如果是负数,那么高位移入1还是0不一定,这是Implementation-defined的,对于x86平台的gcc编译器,最高位移入1, 也就是仍保持负数的符号位,这种处理方式对负数仍然保持了“右移1位相当于除以2”的性质。
示例:
// 将一个数循环左移
#include <stdio.h>
#include <stdlib.h>
typedef unsigned int u32_t;
#if 0
u32_t left_shift(u32_t a, int n)
{
n %= 32;
int i;
for(i = 0; i < n; ++i)
a = (a << 1)| (a >> 31);
return a;
}
#else
u32_t left_shift(u32_t a, int n)
{
n %= 32;
a = (a << n) | (a >> (32-n));
return a;
}
#endif
int main(int argc, char *argv[])
{
int a = 0x12345678;
int n = atoi(argv[1]);
printf("0x%x\n", left_shift(a, n));
return 0;
}
1、设置位
a |= 1<<i; // 设置 a 的第 i 位为 1
2、清除位
a &= ~(1<<i); // 设置 a 的第 i 位为 0
3、测试位
if (a & (1<<i)) // 设置 a 的第 i 位是否为 1
if (!(a & (1<<i))) // 设置 a 的第 i 位是否为 0
if (((a >> i) & 0xF) == 0x9) // 设置 a 的第 i 位至 第 i+4 位是否为 1001b
4、获取位
(a>>i) & 0x1 // 获取 a 的第 i 位
(a>>i) & 0xF // 获取 a 的第 i 位 至 第 i+4 位