1. 程式人生 > >計算機中的原碼,反碼,補碼,以及他們在內存中的存儲形式。

計算機中的原碼,反碼,補碼,以及他們在內存中的存儲形式。

加減法 判斷 組成 sig 等等 同時 解析 數字 技術分享

1.原碼

原碼就是早期用來表示數字的一種方式: 一個正數,轉換為二進制位就是這個正數的原碼。負數的絕對值轉換成二進制位然後在高位補1就是這個負數的原碼

      舉例說明:

      int類型的 3 的原碼是 11B(B表示二進制位), 在32位機器上占四個字節,那麽高位補零就得:

      00000000 00000000 00000000 00000011

      int類型的 -3 的絕對值的二進制位就是上面的 11B 展開後高位補零就得:

      10000000 00000000 00000000 00000011      

      但是原碼有幾個缺點,

a.零分兩種 +0 和 -0 。

b.在進行不同符號的加法運算或者同符號的減法運算的時候,不能直接判斷出結果的正負。需要將兩個值的絕對值進行比較,然後進行加減操作,

最後符號位由絕對值大的決定。於是反碼就產生了。

2.反碼    

正數的反碼就是原碼,負數的反碼等於原碼除符號位以外所有的位取反

      舉例說明:

      int類型的 3 的反碼是

      00000000 00000000 00000000 00000011

      int類型的 -3 的反碼是

      11111111 11111111 11111111 11111100

      除開符號位 所有位 取反

      解決了加減運算的問題,但還是有正負零之分,然後就到補碼了

3.補碼

正數的補碼與原碼相同,負數的補碼為 其原碼除符號位外所有位取反(得到反碼了),然後最低位加1.

      還是舉例說明:

      int類型的 3 的補碼是:

      00000000 00000000 00000000 00000011

      int類型的 -3 的補碼是

      11111111 11111111 1111111 11111101

      就是其反碼加1

總結:

a.正數的反碼和補碼都與原碼相同。

b.負數的反碼為對該數的原碼除符號位外各位取反。

c.負數的補碼為對該數的原碼除符號位外各位取反,然後在最後一位加1  

d.原碼好理解了,但是加減法不夠方便,還有兩個零(正負0)

e.反碼稍微困難一些,解決了加減法的問題,但還是有兩個零

f.補碼理解困難

4.數在內存中都是以補碼形式存在的

對於一個負數-x,它的二進制表示(補碼)求法如下:

a.對x的原碼進行取反運算

b.將取反運算的結果+1

  對於大多數語言來說,char類型的有效範圍是-128~127,那麽如果我們把128這個超過了char類型表示範圍的數賦值給一個char型變量ch,結果會怎樣呢?ch的值會變成0,還是其它值?答案是,ch的值會變成-128,因為128超越了最大值127,於是它開始從最小值開始,搜索一個合適的位置。同樣的道理,將129賦值給ch,ch的值會變成-127。

  還有一個原理就是有符號和無符號數據的區別。我們知道,char也分為signed和unsigned兩種,前者是默認值,而後者的表示範圍是0~255。不管有無符號,這個區間的大小都是256,這也在情理之中,畢竟1個字節由8個位組成,每個位可以取0或1,那麽一共就能表示2^8種不同的情況,2^8就是256。 同時,根據上面的理論,我們可以得出,將255賦值給ch,結果是-1。我們可以分別求出255和-1的補碼,它們都是11111111。當然,這不是什麽巧合,這是有科學道理的。255是unsigned char的最大值,它也是signed char能表示的負數中的最大值。當一個char是unsigned類型的時候,它的第一位自然不會被認為是符號位,所以11111111能表示255,而當這個char是signed類型時,第一位被解析成符號位,結果就是-1了。

c.對繞回和同余的解釋

-336的無符號整數是65200呢?書上說是2的補碼(書中描述):數字0到32767代表它們本身,而數字32768到65535則代表負數,65535代表-1,65534代表-2,依次類推,因此-336由65536-336,也即65200來表示;

d.同余

很多人並不理解補碼。補碼就是同余啊。1000000是正128你知道吧,正負128模256是同余的。加減乘可以直接算也是同余的定理決定的,而不是湊出來的巧合,哪可能湊出這種東西?

8位只能表示256個數,0到255,但我還想表示一些負數怎麽辦呢?就用與該負數同余的正數來表示唄。-1=255,-2=254,等等。

建議脫離算數的思維方式,這其實就是一個環。模任何一個正整數(如256),可以把所有整數分類,比如模256可分256類,0 256 -256...是一類(余0類),1 257 -255...是一類(余1類),等等,這256類可看作環技術分享圖片的元素,你看-128和128是同一個類裏的(余128類),用一個代表另一個罷了。補碼和普通的unsigned integers都是在每類中選一個數,unsigned integers選0到255,補碼表示的有符號整數選-128到127,都是一個數恰好對應一個類。

當你明白這一切後,補碼就是順理成章的事。

e.8位有符號數的列表 內存中8位二進制10000000表示 -128

-1<--->11111111 -2<--->11111110 -126<--->10000010 -127<--->10000001 -128<--->10000000

127<--->01111111 126<--->01111110 125<--->01111101 002<--->00000010 001<--->00000001 000<--->00000000

計算機中的原碼,反碼,補碼,以及他們在內存中的存儲形式。