您現在的位置是:首頁 > 舞蹈首頁舞蹈

關於二進位制的計算方法和原碼、反碼、補碼等操作

由 碼一碼 發表于 舞蹈2022-12-20
簡介*計算機存的時候是存的0b11111111111111111111111111111001在輸出十進位制顯示的時候要回推成十進位制的-71,補碼-1 得到反碼0b11111111111111111111111111111001-10b111

2的10次方除以3的餘數是多少

二。原碼、反碼、補碼

1

什麼是原碼反碼補碼

按照二進位制進行儲存

運算

按照二進位制補碼方式參與運算

原碼

透過8421碼快速計算資料大小

推薦使用計算器

直觀的看資料的大小

反碼

在轉換補碼的過程中的中間值

補碼

參與運算

2

有符號數表示法怎麼做

有符號數

資料有正負之分就是有符號數

資料無正負之分就是無符號數

例如

+

7

-

7

有符號數的組成

符號位

+

數值位

例如

int

a

=+

7

所佔位元組數4b

32

第一個0就是符號位

0

表示正數

1

表示負數

0

0000000

00000000

00000000

00000111

回顧

int表示範圍

2

的32次方個數

-

2

的31次方

+

2

的31次方

-

1

//有一位是符號位 所以31次方

那麼

+

7

-

7

在計算機中如何儲存

程式碼表示

//int a=+7;

int

a

=

0b00000000000000000000000000000111

//原反補 一樣

System

out

println

a

);

//十進位制表示形式 7

//int b=-7;

int

a

=

0b10000000000000000000000000000111

System

out

println

a

);

//十進位制表示形式 -2147483641

/*

如何表示: 是負數所以符號位是1

0b10000000000000000000000000000111 ?

十進位制表示是 -2147483641 並沒有顯示-7

解釋:計算機儲存有符號數是按照補碼的形式存進去的。

0b10000000000000000000000000000111 不是補碼 -7是原碼

總結:

1,計算機儲存有符號數都是按照補碼的形式儲存的

2,正數的原碼,反碼,補碼都是一樣的

3,負數的原碼,反碼,補碼不一樣,

所以如果你直接寫int b=-7 計算機會幫你把它轉成補碼儲存

0b10000000000000000000000000000111這個資料是-7的原碼

如果你儲存這個資料計算機就會把該資料當成補碼去存

(該資料是-7的原碼 會被認為是其他資料透過計算之後的補碼)

原: 符號位+數值位(資料的絕對值)

反: 除了符號位不變 其它全部是1變0,0變1

補: 在反碼的基礎上+1;

再次計算-7

原: 0b10000000000000000000000000000111

反: 0b11111111111111111111111111111000

補: 0b11111111111111111111111111111001 //+1

*/

int

b

=

0b11111111111111111111111111111001

System

out

pirintln

b

);

// 會幫你轉換成原碼然後再顯示十進位制 -7;

/*

計算機存的時候是存的0b11111111111111111111111111111001

在輸出十進位制顯示的時候要回推成十進位制的-7

1,補碼-1 得到反碼

0b11111111111111111111111111111001

-1

0b11111111111111111111111111111000

2,剩下符號位不變其餘 1變0,0變1

0b10000000000000000000000000000111

*/

三、位邏輯運算子

1、概念

位運算:(二進位制位或者是bit位)

計算機中所有的計算到計算機底層中都會變成位運算(二進位制位的運算) 位運算可以提高程式的效率,而且以後我們研究jdk或者某些框架的原碼裡邊有很多地方都會用到位運算

2、分類

雙目運算子:連線兩個運算元

&: 按位與 規則: 兩個同為1時候才為1

|: 按位或 規則: 兩個中只要有一個為1結果就是1

^: 按位異或 規則: 兩個中不同為1 相同為0

單目運算子: 運算元只有一個

~: 按位取反 規則: 1變0,0變1(包括符號位在內)

注意:位運算連線的運算元是——數值型別(二進位制)

位運算表示式的結果是——數值型別

1

按位與

&

規則

兩個同為1時候才為1

// 3 & 4 的結果

分析

/*

1 要先轉換成二進位制位 並且全是二進位制的補碼形式! //正數原反補 一樣

3 補碼 0b00000000000000000000000000000011

4 補碼 0b00000000000000000000000000000100

2 操作 ——————————————————

結果0b00000000000000000000000000000000 //十進位制也就是0

*/

int

a

=

3

&

4

System

out

println

a

);

2

按位或

|

規則

兩個中只要有一個為1結果就是1

// 3 | 4 的結果

/*

1 要先轉換成二進位制位 並且全是二進位制的補碼形式! //正數原反補 一樣

3 補碼 0b00000000000000000000000000000011

4 補碼 0b00000000000000000000000000000100

2 操作 ——————————————————-

結果 0b00000000000000000000000000000111 //十進位制也就是7

*/

int

a

=

3

|

4

System

out

pirintln

a

);

3

按位異或

^

規則

兩個中不同為1

相同為0

// 3 ^ 4 的結果

/*

1 要先轉換成二進位制位 並且全是二進位制的補碼形式! //正數原反補 一樣

3 補碼 0b00000000000000000000000000000011

4 補碼 0b00000000000000000000000000000100

2 操作 ——————————————————-

結果 0b00000000000000000000000000000111 //十進位制也就是7

*/

int

a

=

3

^4

System

out

println

a

);

一個數據對相同的資料異或兩次其值不變

a兩次異或b結果不變

a^b^b

==

a

int

a

=

3

int

b

=

4

System

out

println

a^b^b

);

/*

3 補碼 0b00000000000000000000000000000011

4 補碼 0b00000000000000000000000000000100

—————————————————————— 第一次異或不同為1 相同為0

結果 0b00000000000000000000000000000111

4 0b00000000000000000000000000000100

——————————————————————第二次異或不同為1 相同為0

0b00000000000000000000000000000011 //補碼 3

*/

4

按位取反

1

變0

0

變1

包括符號位在內

// ~3 的結果

/*

1 要先轉換成二進位制位 並且全是二進位制的補碼形式! //正數原反補 一樣

3 補碼 0b00000000000000000000000000000011

2 操作 ——————————————————-補碼按位取反還是補碼

結果 0b11111111111111111111111111111100 //補碼

//首先符號位是1 是負數 其次 這是補碼 要算反碼

現在已知道補碼求原碼

補碼:0b11111111111111111111111111111100

- 1

————————————————————-

反碼:0b11111111111111111111111111111011 //符號位不變 取反

原碼:0b10000000000000000000000000000100 //原碼 十進位制顯示 -4

*/

int

a

=

~3

System

out

println

a

);

5

互為取反

int

a

=

~6

System

out

println

a

);

//-7

//0b00000000000000000000000000000110 +6

//0b11111111111111111111111111111001 取反:結果是負數 是補碼

//0b11111111111111111111111111111000 反碼

//0b10000000000000000000000000000111 原碼:-(1+2+4)=-7

//6取反就是-7 那麼-7取反呢

System

out

println

~

-

7

);

//6

//0b10000000000000000000000000000111 -7原碼

//0b11111111111111111111111111111000 -7反碼

//0b11111111111111111111111111111001 -7補碼

//0b00000000000000000000000000000110 -7取反 結果是整數 2+4=6

3、案例:資料互動

需求:

已知兩個整數變數a = 10,b = 20,使用程式實現這兩個變數的資料交換;不允許出現第三方變數

思路:

使用異或,一個數據對相同的資料異或兩次其值不變

程式碼:

public

static

void

main

String

[]

args

) {

int

a

=

10

int

b

=

20

a

=

a

^

b

//a = 10 ^ 20;

b

=

a

^

b

//b = 10 ^ 20 ^ 20;

a

=

a

^

b

//a = 10 ^ 20 ^ 10;

System

out

println

a

);

System

out

println

b

);

}

注意:

以後編碼中,更多的還是選擇定義第三方變數

四、位移運算子

1、分類

位移運算子的分類

<<

左移

規則

讓運算元乘以2的n次冪

n是移動的位數

>>

右移

規則

讓運算元除以2的n次冪

n是移動的位數

>>>

無符號右移

規則

讓運算元除以2的n次冪

n是移動的位數xxxxxxxxxx

#

四、位移運算子##

1

、分類位移運算子的分類

<<

左移

規則

讓運算元乘以2的n次冪

n是移動的位數

>>

右移

規則

讓運算元除以2的n次冪

n是移動的位數

>>>

無符號右移

規則

讓運算元除以2的n次冪

n是移動的位數java

2、左位移操作 <<

規則

讓運算元乘以2的n次冪

n是移動的位數

左邊符號位丟棄

右邊補0

格式

運算元

<<

往左位移的位數

操作的是二進位制位

int

a

=

3

<<

2

//運算元 3*2^2 =3*4=12

System

out

println

a

);

/*

補碼 0b00000000000000000000000000000011

位移 0b000000000000000000000000000011

右邊空出兩位補0 左邊的兩位就被擠掉了

結果:0b00000000000000000000000000001100

符號位是0 是正數 原反補一致

//十進位制表示 12

*/

負數左移

int

b

=-

3

<<

2

System

out

println

b

);

/*

-3

原碼 0b10000000000000000000000000000011

反碼 0b11111111111111111111111111111100

補碼 0b11111111111111111111111111111101

左移 0b111111111111111111111111111101

補齊:0b11111111111111111111111111110100 補碼 -1

反碼 0b11111111111111111111111111110011

原碼 0b10000000000000000000000000001100 原碼 1100=-12

*/

int

i

=

21

//00000000000000000000000000010101

int

x1

=

i

<<

2

//21*2^2=84 //00000000000000000000000001010100 =4+16+64=84

int

x2

=

i

<<

3

//21*2^3=168 //00000000000000000000000010101000 =8+32+128=168

int

x3

=

i

<<

26

//21*2^26=1409286144 //01010100000000000000000000000000

int

x4

=

i

<<

27

//21*2^27=-1476395008 //10101000000000000000000000000000 變成負數了

int

i

=-

21

//10000000000000000000000000010101 原碼

//11111111111111111111111111101010 反碼

//11111111111111111111111111101011 補碼(反碼+1)

int

x1

=

i

<<

2

//-21*2^2=-84

//11111111111111111111111111101011 補碼

//11111111111111111111111110101100 位移補0 求原碼

//11111111111111111111111110101011 反碼

//10000000000000000000000001010100 原碼 結果是 4+16+64=84 符號是1 結果是-84

int

x2

=

i

<<

3

//-21*2^3=-168

int

x3

=

i

<<

26

//-21*2^26=-1409286144

int

x4

=

i

<<

27

//-21*2^27=1476395008

//11111111111111111111111111101011 補碼

//01011000000000000000000000000000 位移27位 補0 符號位0 變成正數

結論

<<

在一定的範圍內每向左移動移動一位相當於

*

2

最高效的計算

2

*

8

2

<<

3

或者

8

<<

1

3、右位移操作 >>

規則

讓運算元除以2的n次冪

n是移動的位數

格式

運算元

>>

往右位移的位數

操作的是二進位制位

int

a

=

32

>>

2

//運算元 32/2^2 =32/4=8

System

out

println

a

);

/*

32補碼 0b00000000000000000000000000100000

位移 0b000000000000000000000000001000

左邊邊空出兩位補0(符號位是啥補啥) 右邊的兩位就被擠掉了

結果:0b00000000000000000000000000001000

符號位是0 是正數 原反補一致

//十進位制表示 8

*/

負數情況

int

b

=-

32

>>

2

//運算元 -32/2^2 =-32/4=-8

System

out

println

a

);

/*

-32原碼: 0b10000000000000000000000000100000

取反

反碼: 0b11111111111111111111111111011111 (符號位不變 其他1變0 0變1)

+ 1

補碼: 0b11111111111111111111111111100000

右位移: 0b111111111111111111111111111000

左邊邊空出兩位補1(符號位是啥補啥 現在符號位是1 補1) 右邊的兩位就被擠掉了

結果補碼:0b11111111111111111111111111111000 //這個也是補碼

當輸出顯示的時候要回推顯示原碼形式

0b11111111111111111111111111111000

- 1

反碼:0b11111111111111111111111111110111

原碼:0b10000000000000000000000000001000 //十進位制表示 -8

*/

int

i

=

21

//00000000000000000000000000010101

int

x1

=

i

>>

2

//00000000000000000000000000000101 1+4=5

int

x2

=

i

>>

3

//00000000000000000000000000000010 2=2;

int

x3

=

i

>>

26

//00000000000000000000000000000000 0

int

x4

=

i

>>

27

//00000000000000000000000000000000 0

int

i

=-

21

//10000000000000000000000000010101 原碼

//11111111111111111111111111101010 反碼

//11111111111111111111111111101011 補碼(反碼+1)

int

x1

=

i

>>

2

//11111111111111111111111111101011 補碼

//11111111111111111111111111111010 右移2位 符號位是啥補啥 已知補碼求原碼先求反碼(補碼-1)

//11111111111111111111111111111001 反碼

//10000000000000000000000000000110 //結果是 2+4=6 符號位是1是負數 =-6

int

x2

=

i

>>

3

//-3

int

x3

=

i

>>

26

//-1

int

x4

=

i

>>

27

//-1

//11111111111111111111111111101011 補碼

//11111111111111111111111111111111 右移27位 符號位是啥補啥 已知補碼求原碼先求反碼(補碼-1)

//11111111111111111111111111111110 反碼

//10000000000000000000000000000001 結果是 1 符號位是1是負數 =-1

結論

>>

在一定的範圍內每向右移動移動一位相當於

/

2

4、無符號右移: >>>

關於二進位制的計算方法和原碼、反碼、補碼等操作