天天看點

C語言負數的移位運算

在c 中左移也就是所說的邏輯移位,右端補0,而右移是算數移位,左端補齊的是最高位的符号位。

故負數左移,有可能變成正數,但負數右移,肯定還是負數。

用16進制的形式對資料進行指派,這16進制的數代表的是補碼。

    i = 0xfffffff7; //0xfffffff7是補碼,而不是原碼,故i = -9

    printf("%d %x\n", i, i);

    i = -9;

    printf("%d %x\n", i, i);  //故兩個printf輸出結果相同

/**********************************************************************
 * Compiler: GCC
 * Last Update:  Tue 01 May 2012 07:31:44 PM CST
 ************************************************************************/
#include <stdio.h>

int main(int argc, char **argv)
{   
    int i = 0x8000000f; //這裡的0x8000000f為int型資料的補碼形式
    int j = i >> 3; //右移是算術移位,左端補齊的是符号位
    int k = i << 1; //左移是邏輯移位,右端補0
    printf("%d %x\n", i, i); 
    printf("%d %x\n", j, j); 
    printf("%d %x\n", k, k); 

    i = -9;
    printf("%d %x\n", i, i); 
    i = 0xfffffff7;
    j = i >> 3;
    k = i << 1;
    printf("%d %x\n", i, i); 
    printf("%d %x\n", j, j); 
    printf("%d %x\n", k, k); 


    return 0;
}
           

運作結果:

-2147483633 8000000f

-268435455 f0000001

30 1e

-9 fffffff7

-9 fffffff7

-2 fffffffe

-18 ffffffee

-9的8位補碼表示是1111 0111,即0xf7,這裡是int型,擴充成32位表示是0xfffffff7。也可以直接用32位的形式寫出-9的補碼形式。

對于signed類型的擴充,看該資料的最高位,為1,則擴充的所有位都為1,為0,則擴充的位都為0,故0xf7擴充成32位是0xfffffff7。

這裡 -9 << 1 = -18。不能簡單的從左移就相當于乘以2來了解,要從-9的補碼是0xfffffff7f去考慮。

繼續閱讀