
提示:以下是本篇文章正文內容文中第四部分代碼例子來自于此篇博客,衷心感謝此博主的分享《https://blog.csdn.net/weixin_42167759/article/details/85624722》
自己加了不少內容上去,更好去理解。
Windows下進行socket網絡編程,編寫校驗和時遇到的問題,記錄如下。
位移位運算符是將數據看成二進制數,對其進行向左或向右移動若干位的運算。
位移位運算符分為左移和右移兩種,均為雙目運算符。
例如: 8>>3 (意思是8向右移動3位)第一運算對象是移位對象,第二個運算對象是所移的二進制位數。邏輯移位
簡單理解就是物理上按位進行的左右移動,兩頭用0進行補充,不關心數值的符號問題。
邏輯左移/右移指令只有它們的移位方向不同,移位后空出的位都補0。算術移位
同樣也是物理上按位進行的左右移動,兩頭用0或1進行補充,但必須確保符號位不改變。
算術左移SAL把目的操作數的低位向高位移,空出的低位補0;
算術右移SAR把目的操作數的高位向低位移,空出的高位用最高位(符號位,0或1)填補 。但我們好奇的是“i<<3”和“i>>3”到底采用的是算術還是邏輯移位呢?
當向左邊移動3位,采用的什么方式的移動???
#includeint main()
{unsigned int ui = 8;
ui = ui<< 3;
printf("ui = %d 無符號類型左移(正數)\n", ui);
int i = 8;
i = i<< 3;
printf("i = %d 有符號類型左移(正數)\n", i);
int fi = -8;
fi = fi<< 3;
printf("fi = %d 有符號類型左移(負數)\n", fi);
return 0;
} 結果顯示:
ui = 64 無符號類型左移(正數)
i = 64 有符號類型左移(正數)
fi = -64 有符號類型左移(負數)
分析:
注意數在計算機里的存儲和表示都是補碼!!!
無符號
8 00000000 00000000 00000000 00001000
<----- 左移3位,低位補0
64 00000000 00000000 00000000 01000000
有符號(即最高位為符號位)
8 00000000 00000000 00000000 00001000
<----- 左移3位,低位補0
64 00000000 00000000 00000000 01000000
有符號(即最高位為符號位)
-8 11111111 11111111 11111111 11111000
<----- 左移3位,低位補0
-64 11111111 11111111 11111111 11000000結論:左移時總是移位和補零,無論是有符號還是無符號都可看作進行了邏輯左移。
當向右邊移動3位,采用的什么方式的移動???
#includeint main()
{unsigned int ui = 8;
ui = ui >>3;
printf("ui = %d 無符號類型右移(正數)\n", ui);
int i = 8;
i = i >>3;
printf("i = %d 有符號類型右移(正數)\n", i);
int fi = -8;
fi = fi >>3;
printf("fi = %d 有符號類型右移(負數)\n", fi);
return 0;
} 結果顯示:
ui = 1 無符號類型左移(正數)
i = 1 有符號類型左移(正數)
fi = -1 有符號類型左移(負數)
分析:
注意數在計算機里的存儲和表示都是補碼!!!
無符號
8 00000000 00000000 00000000 00001000
----->右移3位,高位補0
1 00000000 00000000 00000000 00000001
有符號(即最高位為符號位)
8 00000000 00000000 00000000 00001000
----->右移3位,高位補符號位,即0
1 00000000 00000000 00000000 00000001
有符號(即最高位為符號位)
-8 11111111 11111111 11111111 11111000
----->右移3位,高位補符號位,即1
-1 11111111 11111111 11111111 11111111結論:
右移時無符號數是移位和補零,此時稱為邏輯右移;
右移時而有符號數大多數情況下是移位和補最左邊的位(也就是補最高有效位),移幾位就補幾位,此時稱為算術右移。
其實可以理解為左移擴大,右移縮小。
例如如下c代碼:
int a = 8;
int b1 = a * 4
int b2 = a<< 2 //左移2位相當于擴大4倍
int b3 = a / 4
int b4 = a >>2 //右移2位相當于縮小4倍結果
b1 = b2 = 4
b3 = b4=1
但是有時候想把兩個8位二進制數拼成一個16位二進制,“左移<<” 與 "右移>>"就很重要。例如 00001000 與 00000011 拼接成00001000 00000011:
分析:
二進制
a 00001000 <--左移8位,低位補0
a 00001000 00000000
+
b 00000011
——————————————————————————
得到目標結果 00001000 00000011在scoket網絡編程,例如計算校驗和時,都知道是以16位二進制進行相加,那么計算機是以8位二進制讀取,如何將兩個8位數字拼成一個16位數字,就是利用上方原理講解。
具體可見之前寫的筆記 《校驗和之概念、計算原理、檢驗原理、實例計算、代碼編程,力薦力薦力薦》
6、總結左移時總是移位和補零,無論是有符號還是無符號都可看作進行了邏輯左移。
右移時無符號數是移位和補零,此時稱為邏輯右移;
右移時而有符號數大多數情況下是移位和補最左邊的位(也就是補最高有效位),移幾位就補幾位,此時稱為算術右移。
碼字不易,謝謝點贊!!!
碼字不易,謝謝點贊!!!
碼字不易,謝謝點贊!!!
你是否還在尋找穩定的海外服務器提供商?創新互聯www.cdcxhl.cn海外機房具備T級流量清洗系統配攻擊溯源,準確流量調度確保服務器高可用性,企業級服務器適合批量采購,新人活動首月15元起,快前往官網查看詳情吧
本文標題:從代碼角度理解:C語言中的“左移<<“與“右移>>“,且結合應用場景-創新互聯
標題網址:http://www.yijiale78.com/article22/dodjjc.html
成都網站建設公司_創新互聯,為您提供ChatGPT、建站公司、網站改版、網站導航、面包屑導航、標簽優化
聲明:本網站發布的內容(圖片、視頻和文字)以用戶投稿、用戶轉載內容為主,如果涉及侵權請盡快告知,我們將會在第一時間刪除。文章觀點不代表本網站立場,如需處理請聯系客服。電話:028-86922220;郵箱:631063699@qq.com。內容未經允許不得轉載,或轉載時需注明來源: 創新互聯