C语言复习0.2——位运算

C语言复习0.2


位运算

可以使用C对变量中的个别位进行操作。您可能对人们想这样做的原因感到奇怪。这种能力有时确实是必须的,或者至少是有用的。C提供位的逻辑运算符和移位运算符。在以下例子中,我们将使用二进制计数法写出值,以便您可以了解对位发生的操作。在一个实际程序中,您可以使用一般的形式的整数变量或常量。例如不适用00011001的形式,而写为25或者031或者0x19.在我们的例子中,我们将使用8位数字,从左到右,每位的编号是7到0。

位逻辑运算符

4个位运算符用于整型数据,包括char.将这些位运算符成为位运算的原因是它们对每位进行操作,而不影响左右两侧的位。请不要将这些运算符与常规的逻辑运算符(&& 、||和!)相混淆,常规的位的逻辑运算符对整个值进行操作。

按位取反~

一元运算符~将每个1变为0,每个0变为1,如下:

    ~(10011010)
    01100101

假设a是一个unsigned char,已赋值为2.在二进制中,2是00000010.于是-a的值为11111101或者253。请注意该运算符不会改变a的值,a仍为2。

    unsigned char a = 2;   //00000010
    unsigned char b = ~a;  //11111101
    printf("ret = %d\n", a); //ret = 2
    printf("ret = %d\n", b); //ret = 253

位与(AND) : &

二进制运算符&通过对两个操作数逐位进行比较产生一个新值。对于每个位,只有两个操作数的对应位都是1时结果才为1。

      (10010011) 
    & (00111101) 
    = (00010001)

C也有一个组合的位与-赋值运算符:&=。下面两个将产生相同的结果:

    val &= 0377
    val = val & 0377

ps:
一个数 &1的结果就是取二进制的最末位。这可以用来判断一个整数的奇偶,二进制的最末位为0表示该数为偶数,最末位为1表示该数为奇数。

位或(OR) : |

二进制运算符|通过对两个操作数逐位进行比较产生一个新值。对于每个位,如果其中任意操作数中对应的位为1,那么结果位就为1.

       (10010011)
     | (00111101)
     = (10111111)

C也有组合位或-赋值运算符: |=

    val |= 0377
    val = val | 0377

ps:
or运算通常用于二进制特定位上的无条件赋值,例如一个数or 1的结果就是把二进制最末位强行变成1。如果需要把二进制最末位变成0,对这个数or 1之后再减一就可以了。

位异或 : ^

二进制运算符^对两个操作数逐位进行比较。对于每个位,如果操作数中的对应位有一个是1(但不是都是1),那么结果是1.如果都是0或者都是1,则结果位0.

       (10010011)
     ^ (00111101)
     = (10101110)

^=不说了自行脑补

用法

打开位
flag | ~flag

     (10011010)
    |(01100101)
    =(11111111)

关闭位
flag & ~flag

     (10011010)
    &(01100101)
    =(00000000)

转置位
flag ^ 0xff

     (10010011)
    ^(11111111)
    =(01101100)

交换两个数

//a ^ b = temp;
//a ^ temp = b;
//b ^ temp = a
 (10010011)
^(00100110)
=(10110101)

 (10110101)
^(00100110)
  10010011

移位运算符

左移

左移运算符<<将其左侧操作数的值的每位向左移动,移动的位数由其右侧操作数指定。空出来的位用0填充,并且丢弃移出左侧操作数末端的位。
在下面例子中,每位向左移动两个位置。

    (10001010) << 2
    (00101000)

左移一位相当于原值*2.

    1 << 1 = 2;
    2 << 1 = 4;
    4 << 1 = 8;
    8 << 2 = 32

右移

右移运算符>>将其左侧的操作数的值每位向右移动,移动的位数由其右侧的操作数指定。丢弃移出左侧操作数有段的位。对于unsigned类型,使用0填充左端空出的位。对于有符号类型,结果依赖于机器。空出的位可能用0填充,或者使用符号(最左端)位的副本填充。

    //有符号值
    (10001010) >> 2
    (00100010)     //在某些系统上的结果值

    (10001010) >> 2
    (11100010)     //在另一些系统上的结果

    //无符号值
    (10001010) >> 2
    (00100010)    //所有系统上的结果值

用法

移位运算符能够提供快捷、高效(依赖于硬件)对2的幂的乘法和除法。

number << n number乘以2的n次幂
number >> n 如果number非负,则用number除以2的n次幂

你可能感兴趣的:(C-C++,c语言,位运算)