Chapter02-信息的存儲(chǔ)

1.信息的存儲(chǔ)

  • 通常情況下,程序?qū)?nèi)存視為一個(gè)非常大的數(shù)組。數(shù)組的元素是由一個(gè)個(gè)的字節(jié)組成,每個(gè)字節(jié)都由一個(gè)唯一的數(shù)字來(lái)表示,稱之為地址。這些所有地址的集合稱為虛擬地址空間。
信息的存儲(chǔ).jpg

2.字節(jié)

  • 1個(gè)字節(jié)是由8個(gè)位組成,在二進(jìn)制中,每一位的值可能有0或者1兩種狀態(tài)。當(dāng)這8個(gè)位全為0時(shí),表示一個(gè)字節(jié)的最小值;當(dāng)這8個(gè)位全為1時(shí),表示最大值;如果用十進(jìn)制來(lái)表示,那么一個(gè)字節(jié)的取值范圍就在[0,255]之間。上面這種按照一位一位表示數(shù)據(jù)的方式稱為位模式。
位模式.jpg

3.十六進(jìn)制表示位模式

  • 在C語(yǔ)言中,十六進(jìn)制數(shù)是以0X或0x開(kāi)頭。字母部分可以是全部大寫(xiě)或全部小寫(xiě)或者大小寫(xiě)混合。
十六進(jìn)制、二進(jìn)制、十進(jìn)制.jpg
  • 二進(jìn)制與十六進(jìn)制之間的轉(zhuǎn)換:將二進(jìn)制數(shù)從右向左,每四位為一組來(lái)轉(zhuǎn)換成相應(yīng)的十六進(jìn)制數(shù)。如果總位數(shù)不是4的倍數(shù),那么最左邊的一組會(huì)出現(xiàn)小于4位的情況,這時(shí)將前面進(jìn)行補(bǔ)0。接著,將每4位為一組的二進(jìn)制數(shù)進(jìn)行一一轉(zhuǎn)換即可得到十六進(jìn)制數(shù)。
二進(jìn)制與十六進(jìn)制轉(zhuǎn)換.jpg
  • 如何將形如2的n次方的數(shù)快速轉(zhuǎn)換為二進(jìn)制數(shù)?
2^0 = 1          0個(gè)0
2^1 = 10         1個(gè)0
2^2 = 100        2個(gè)0
2^3 = 1000       3個(gè)0
2^4 = 10000      4個(gè)0
2^5 = 100000     5個(gè)0
....
2^n = 1000...000 n個(gè)0

n = i + 4j:n除以4,j是商、i是余數(shù),i的可能取值是0、1、2、3,因此與之對(duì)應(yīng)的十六進(jìn)制數(shù)是1、2、4、8

例如2^13, n = 13 = 1 + 4 * 3,因此2^13 = 0x2000
  • 十進(jìn)制與十六進(jìn)制之間的轉(zhuǎn)換:使用輾轉(zhuǎn)相除法,每次使用得到的商來(lái)除以16,直到得到的商不能被16整除為止。將得到的余數(shù)用16進(jìn)制來(lái)表示,然后自下而上書(shū)寫(xiě)即可得到十六進(jìn)制表示。
十進(jìn)制轉(zhuǎn)換成十六進(jìn)制數(shù).jpg

4.字長(zhǎng)Words

  • 字長(zhǎng)決定了虛擬地址空間最大值可以到多少,對(duì)于32位機(jī)器,虛擬地址空間最大為4GB;64位機(jī)器,虛擬地址空間最大為16EB。
字長(zhǎng).jpg
  • 大多數(shù)64位的機(jī)器做了向下兼容,因此32位機(jī)器編譯的程序也可以運(yùn)行在64位機(jī)器上。在64位機(jī)器上,可以通過(guò)命令gcc -m32 -o hello32 hello.c編譯生成可以在32位機(jī)器上運(yùn)行的程序。通過(guò)修改編譯選項(xiàng)gcc -m64 -o hello64 hello.c,就可以編譯生成在64位機(jī)器上運(yùn)行的程序。
不同類型數(shù)據(jù)占用不同字節(jié)空間.jpg

5.地址和字節(jié)序

  • 一個(gè)int類型的變量x=0x01234567,假設(shè)地址位于0x100處。由于int類型占4個(gè)字節(jié),因此x被存儲(chǔ)在地址為0x100~0x103的內(nèi)存處。
大端模式與小端模式.jpg
  • 大端模式:最高有效字節(jié)存儲(chǔ)在最前面即低地址處。IBM和Sun公司的機(jī)器大多采用大端法。

  • 小端模式:最低有效字節(jié)存儲(chǔ)在最前面即低地址處。大多數(shù)intel兼容機(jī)采用小端模式。

    // 判斷大、小端模式測(cè)試程序
    #include <stdio.h>
    
    typedef unsigned char* byte_pointer;
    
    void show_bytes(byte_pointer start, int len) {
        int i;
        for(i = 0; i < len; i++) {
            printf("%.2x", start[i]);
        }
        printf("\n");
    }
    
    void show_int(int x) {
        show_bytes((byte_pointer) &x, sizeof(x));
    }
    
    

6.存儲(chǔ)字符串

  • C語(yǔ)言中的字符串被編碼為以NULL字符結(jié)尾的字符數(shù)組,其中結(jié)尾字符的十六進(jìn)制表示為0x00。使用ASCII碼來(lái)表示字符,在任何系統(tǒng)上都會(huì)得到相同的結(jié)果。于是,文本數(shù)據(jù)比二進(jìn)制數(shù)據(jù)具有更強(qiáng)的平臺(tái)獨(dú)立性。
字符串存儲(chǔ).jpg

7.布爾代數(shù)

  • C語(yǔ)言中,支持按位進(jìn)行布爾運(yùn)算。具體如下圖所示:
布爾代數(shù).jpg
C語(yǔ)言中的布爾運(yùn)算.jpg

8.位掩碼運(yùn)算

  • 對(duì)于操作數(shù)0x89ABCDEF,我們希望得到該操作數(shù)的最低有效字節(jié)的值EF,可以通過(guò)&上0xFF這樣就得到了最低有效字節(jié)0x000000EF;
位掩碼運(yùn)算.jpg

9.邏輯運(yùn)算

  • 邏輯運(yùn)算中,所有非零的參數(shù)都表示為true,只有參數(shù)0表示為false。邏輯運(yùn)算的結(jié)果只有兩種true/false,而位運(yùn)算只有在特殊的數(shù)值條件下才會(huì)得到0或者1。
邏輯運(yùn)算.jpg

10.移位運(yùn)算

  • 對(duì)于8位二進(jìn)制數(shù)01100011,左移一位就是丟棄最高的1位,并在右端補(bǔ)1個(gè)0,具體結(jié)果如下圖所示:
左移一位.jpg
  • 對(duì)于右移運(yùn)算,分為邏輯右移和算術(shù)右移。邏輯右移和邏輯左移只是在方向上存在差異,邏輯右移一位就是丟棄最低的1位,并在左端補(bǔ)一個(gè)0。
邏輯右移一位.jpg
  • 對(duì)于算術(shù)右移,以下以10010101為例說(shuō)明。當(dāng)算術(shù)右移的操作對(duì)象的最高位等于0時(shí),算術(shù)右移等于邏輯右移,兩者沒(méi)有任何差別;當(dāng)操作數(shù)的最高位為1時(shí),算術(shù)右移后,左端需要補(bǔ)1而不是補(bǔ)0;
算術(shù)右移且操作數(shù)的最高位等于0.jpg
算術(shù)右移且操作數(shù)的最高位等于1.jpg
  • 雖然C語(yǔ)言中并沒(méi)有明確的規(guī)定有符號(hào)數(shù)應(yīng)該使用哪一種類型的右移方式,但實(shí)際上幾乎所有的編譯器以及機(jī)器的組合都是對(duì)有符號(hào)數(shù)使用算術(shù)右移;對(duì)于無(wú)符號(hào)數(shù),右移一定是邏輯右移;

11.參考資料

[1].本文圖片來(lái)源,侵權(quán)必刪:https://www.bilibili.com/video/BV1cD4y1D7uR?p=6

最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請(qǐng)聯(lián)系作者
【社區(qū)內(nèi)容提示】社區(qū)部分內(nèi)容疑似由AI輔助生成,瀏覽時(shí)請(qǐng)結(jié)合常識(shí)與多方信息審慎甄別。
平臺(tái)聲明:文章內(nèi)容(如有圖片或視頻亦包括在內(nèi))由作者上傳并發(fā)布,文章內(nèi)容僅代表作者本人觀點(diǎn),簡(jiǎn)書(shū)系信息發(fā)布平臺(tái),僅提供信息存儲(chǔ)服務(wù)。

相關(guān)閱讀更多精彩內(nèi)容

友情鏈接更多精彩內(nèi)容