圖解計算機中數(shù)據(jù)的表示形式
作者個人研發(fā)的在高并發(fā)場景下,提供的簡單、穩(wěn)定、可擴展的延遲消息隊列框架,具有精準的定時任務(wù)和延遲隊列處理功能。自開源半年多以來,已成功為十幾家中小型企業(yè)提供了精準定時調(diào)度方案,經(jīng)受住了生產(chǎn)環(huán)境的考驗。為使更多童鞋受益,現(xiàn)給出開源框架地址:https://github.com/sunshinelyz/mykit-delay
寫在前面
應(yīng)很多小伙伴的要求,我開了一個新的專題【程序員進階系列】,在這個專題中,我會跟大家分享有關(guān)計算機和軟件的一系列 底層 知識,讓小伙伴們更好的理解計算機的底層架構(gòu)知識,能夠更好的提高自身的編程能力和軟件設(shè)計能力。本篇就作為整個專題的開篇,希望能夠為小伙伴們帶來實質(zhì)性的幫助。
數(shù)據(jù)的表示
在計算機中,所有的數(shù)據(jù)都是以二進制的形式進行表示的,也就是說,在計算機中使用0和1來表示所有的數(shù)據(jù)。而我們?nèi)粘I钪械臄?shù)字都是10進制的,那我們平時使用的數(shù)字如果在計算機中表示時就需要進行進制的轉(zhuǎn)換。
進制轉(zhuǎn)換
R進制轉(zhuǎn)10進制
R進制轉(zhuǎn)10進制可以使用按權(quán)展開的方法,具體的操作就是:將R進制數(shù)的每一位數(shù)值使用R^k^表示,底數(shù)是R,指數(shù)是k。其中,k與該位和小數(shù)點之間的位置有關(guān)。當(dāng)這個位置位于小數(shù)據(jù)左邊時,k的值是從小數(shù)點向左依次數(shù)的個數(shù),需要注意的是:緊鄰小數(shù)點的數(shù)字位置為0,接下來是1,2...依次類推。同樣的,如果這個位置在小數(shù)點的右邊,則緊鄰小數(shù)據(jù)點位置的數(shù)字從-1開始,依次向右數(shù)為-2,-3等等,依此類推。
例如,我們給出一個二進制數(shù)字,11010101.01,轉(zhuǎn)換為10進制數(shù)字為:1 x 2^7^ + 1 x 2^6^ + 0 x 2^5^ + 1 x 2^4^ + 0 x 2^3^ + 1 x 2^2^ + 0 x 2^1^ + 1 x 2^0^ + 0 x 2^-1^ + 1 x 2^-2^。
注:2^7^表示2的7次方。
再比如,我們給出一個八進制數(shù),76128.01,轉(zhuǎn)換為10進制數(shù)字為:7 x 8^4^ +6 x 8^3^ + 1 x 8^2^ + 2 x 8^1^ + 8 x 8^0^ + 0 x 8^-1^ + 1 x 8^-2^
十進制轉(zhuǎn)R進制
十進制轉(zhuǎn)R進制就比較簡單了,這里我們可以使用短除法。
例如,將十進制數(shù)字69轉(zhuǎn)換為二進制的過程如下所示。
得出短除的結(jié)果后,我們需要將余數(shù)倒過來排列即為十進制69轉(zhuǎn)換為二進制的結(jié)果,所以結(jié)果數(shù)據(jù)為:1000101。
二進制與八進制互轉(zhuǎn)
二進制轉(zhuǎn)八進制時,每三位二進制數(shù)表示一個八進制數(shù)。因為在八進制中,總共有8個基數(shù),分別是0~7,逢8進1。而如果要使用二進制來表示時,0的二進制為000,7的二進制為111,所以,每三位二進制數(shù)對應(yīng)一位八進制數(shù)。反過來,每一位八進制數(shù)對應(yīng)三位二進制數(shù)。
具體的劃分策略是,從二進制的低位開始,從低到高,也就是從右向左,每三位二進制數(shù)對應(yīng)一個八進制數(shù),不足三位的前面補0,例如,我們將二進制數(shù):10001110轉(zhuǎn)化為八進制數(shù)的過程,具體如下所示。
所以,二進制數(shù)10001110轉(zhuǎn)化為八進制數(shù)的結(jié)果為216。
同理,八進制轉(zhuǎn)二進制與二進制轉(zhuǎn)八進制正好相反,八進制的每一位對應(yīng)三位的二進制數(shù)。也就是說,將八進制數(shù)的每一位轉(zhuǎn)化成三位的二進制數(shù)即可。
二進制與十六進制互轉(zhuǎn)
在十六進制表示的數(shù)字中,總共有15個基數(shù),為0~15,逢16進1。如果要將二進制數(shù)轉(zhuǎn)化為十六進制數(shù)時,首先要弄清楚每位十六進制數(shù)需要多少為二進制數(shù)表示。在十六進制中,最大的基數(shù)為15,15的二進制表示為:1111,最小的基數(shù)為0,0的二進制數(shù)為0000,也就是說,十六進制的基礎(chǔ)使用二進制表示為 0000~1111,所以,每位十六進制數(shù)需要四位二進制數(shù)表示。
從二進制數(shù)的低位開始,也就是從右側(cè)開始,每四位二進制數(shù)對應(yīng)一位十六進制數(shù)。
例如,我們需要將二進制數(shù)10001110轉(zhuǎn)換為十六進制數(shù),如下所示。
注意:在十六進制中,分別使用A,B,C,D,E,F代表10,11,12,13,14,15。
所以,二進制10001110轉(zhuǎn)化為十六進制的結(jié)果為8E。
十六進制轉(zhuǎn)二進制與二進制轉(zhuǎn)十六進制正好相反,將十六進制的每一位轉(zhuǎn)換為四位二進制數(shù)即可。
數(shù)據(jù)的碼制
在計算機中,帶符號的機器數(shù)可以采用原碼、反碼、補碼和移碼表示,這些編碼稱為碼制。
原碼
在原碼表示中,最高位是符號位,0表示正號,1表示負號,其余的n-1位表示數(shù)值的絕對值,數(shù)值0的原碼有兩種表示形式:
反碼
在反碼中,最高位是符號位,0表示正號,1表示負號,正數(shù)的反碼與原碼相同,負數(shù)的反碼是其絕對值按位取反。數(shù)值0的反碼有兩種表示形式:
補碼
在補碼中,最高位是符號位,0表示正號,1表示負號,正數(shù)的補碼與原碼和反碼相同,負數(shù)的補碼等于其反碼的末位加1。在補碼的表示中,0有唯一的補碼:
移碼
移碼表示法是在數(shù)X上增加一個偏移量來定義的,常用于表示浮點數(shù)中的階碼。如果機器字長為n,規(guī)定偏移量為 2^n-1^。
實際上,在偏移 2^n-1^的情況下,只要將補碼的符號位取反就可以獲得相應(yīng)的移碼。
碼制總結(jié)
我們來看下面的表格,這里,我直接使用八位的二進制數(shù)來表示相應(yīng)的數(shù)值。
碼制 | 數(shù)值1 | 數(shù)值-1 | 1-1 |
---|---|---|---|
原碼 | 0000 0001 | 1000 0001 | 1000 0010 |
反碼 | 0000 0001 | 1111 1110 | 1111 1111 |
補碼 | 0000 0001 | 1111 1111 | 0000 0000 |
移碼 | 1000 0001 | 0111 1111 | 1000 0000 |
通過表格我們發(fā)現(xiàn):
- 正數(shù)的原碼、反碼和補碼是相同的。
- 負數(shù)的反碼是原碼除符號位外,其他位分別取反;
- 負數(shù)的補碼是其反碼的末位加1。
- 移碼是在補碼的基礎(chǔ)上符號位取反得到。
在負數(shù)的原碼和補碼的轉(zhuǎn)換中,我們可以得出如下結(jié)論:
- 負數(shù)的原碼轉(zhuǎn)補碼是在原碼的基礎(chǔ)上除符號位外,其他位取反,然后末位加1。
- 負數(shù)的補碼轉(zhuǎn)原碼是在補碼的基礎(chǔ)上除符號位外,其他位取反,然后末位加1。
也就是說,負數(shù)的原碼轉(zhuǎn)補碼和補碼轉(zhuǎn)原碼的規(guī)則是一樣的。小伙伴們可以根據(jù)表格自行驗證
計算機使用補碼進行加減法運算
我們再來看表格的最后一列 1-1,在計算機中,表示為1+(-1),其正確的結(jié)果應(yīng)該為0。接下來,我們分別分析下使用原碼、反碼、補碼和移碼進行加減法運算的結(jié)果的正確性。
- 表格的第一行中,使用原碼計算的結(jié)果為1000 0010,轉(zhuǎn)換為10進制數(shù)為-2,1-1不等于-2,所以,使用原碼進行加減法運算的結(jié)果是錯誤的。
- 在反碼中,計算1-1的結(jié)果為1111 1111,顯然結(jié)果不為0,所以,使用反碼進行加減法運算的結(jié)果是錯誤的。
- 在補碼中,計算1-1的結(jié)果為0000 0000,結(jié)果為0,所以,使用補碼進行加減法運算的結(jié)果是正確的。
- 在移碼中,計算1-1的結(jié)果為1000 0000,結(jié)果為-0,雖然-0也等于0,但是嚴格意義來講,這個結(jié)果是不正確的。
在計算機中,不會使用移碼進行加減法運算,移碼用于浮點數(shù)的階碼。
本文轉(zhuǎn)載自微信公眾號「冰河技術(shù)」,可以通過以下二維碼關(guān)注。轉(zhuǎn)載本文請聯(lián)系冰河技術(shù)公眾號。