C語言位操作

2021-07-11 10:10:11 字數 2673 閱讀 5655

《朱老師物聯網大講堂》學習筆記

(1).

位與&:只有1&1才是1,其餘全是0,

位或|:只有0|0才是0,其餘全是1,

位取反~:按位操作,

位異或^:1^0 = 1 ,0 ^ 1 = 1,也就是說相異結果是1,與1異或會取反,與0異或無變化,

移位分 左/右 移,物件分 有/無符號數,

只說一點:有符號數右移左側補符號位,叫算術移位,

嵌入式中研究的都是無符號數,

(2).

暫存器操作,讀,改,寫,

特定位清0用&,用0和特定位相&必定為0,其餘位放1,不改變其它位值,

特定位置1用|,用1和特定位相|必定為1,其餘位放0,不改變其它位值,

特定位取反用^,要取反的特定位為1,其它位為0,與其異或,

(3).

bit3~bit7為1,bit23~bit25為1,其餘為0,

( ( 0x1f<<3 ) | ( 7<<23 ) )

上例如果1,0的位置對換,使用取反,

(4)~(5).

是實戰演練,隔斷時間來看看,

下面直接用朱老師的筆記了,一定經常來看,鍛鍊這種運算的思維,

位運算實戰演練1

回顧:要置1用|,用清零用&,要取反用^,~和<< >>用來構建特定二進位制數。

1、給定乙個整型數a,設定a的bit3,保證其他位不變。

a = a | (1<<3)或者 a |= (1<<3)

2、給定乙個整形數a,設定a的bit3~bit7,保持其他位不變。

a = a | (0b11111<<3)或者 a |= (0x1f<<3);

3、給定乙個整型數a,清除a的bit15,保證其他位不變。

a = a & (~(1<<15));或者 a &= (~(1<<15));

4、給定乙個整形數a,清除a的bit15~bit23,保持其他位不變。

a = a & (~(0x1ff<<15));或者 a &= (~(0x1ff<<15));

5、給定乙個整形數a,取出a的bit3~bit8。

思路:第一步:先將這個數bit3~bit8不變,其餘位全部清零。

第二步,再將其右移3位得到結果。

第三步,想明白了上面的2步演算法,再將其轉為c語言實現即可。

a &= (0x3f<<3);

a >>= 3;

6、用c語言給乙個暫存器的bit7~bit17賦值937(其餘位不受影響)。

關鍵點:第一,不能影響其他位;第二,你並不知道原來bit7~bit17中裝的值。

思路:第一步,先將bit7~bit17全部清零,當然不能影響其他位。

第二步,再將937寫入bit7~bit17即可,當然不能影響其他位。

a &= ~(0x7ff<<7);

a |= (937<<7);

位運算實戰演練2

7、用c語言將乙個暫存器的bit7~bit17中的值加17(其餘位不受影響)。

關鍵點:不知道原來的值是多少

思路:第一步,先讀出原來bit7~bit17的值

第二步,給這個值加17

第三步,將bit7~bit17清零

第四步,將第二步算出來的值寫入bit7~bit17

8、用c語言給乙個暫存器的bit7~bit17賦值937,同時給bit21~bit25賦值17.

思路:4.2.4.6的公升級版,兩倍的4.2.4.6中的**即可解決。

分析:這樣做也可以,但是效果不夠高,我們有更優的解法就是合兩步為一步。

(6).

技術公升級:用巨集定義來完成位運算

1、直接用巨集來置位、復位(最右邊為第1位)。 

#define set_nth_bit(x, n)  (x | ((1u)<<(n-1)))

#define clear_nth_bit(x, n) (x & ~((1u)<<(n-1)))

2、擷取變數的部分連續位。例如:變數0x88, 也就是10001000b,若擷取第2~4位,則值為:100b = 4 

#define getbits(x, n, m) ((x & ~(~(0u)<<(m-n+1))<<(n-1)) >> (n-1)) 

分析:這個題目相當於我們4.2.4.5中做的事情,只不過要用巨集來實現。

這個題目相當於是要把x的bit(n-1)到bit(m-1)取出來

複雜巨集怎麼分析:

((x & ~(~(0u)<<(m-n+1))<<(n-1)) >> (n-1))

第一步,先分清楚這個複雜巨集分為幾部分:2部分

(x & ~(~(0u)<<(m-n+1))<<(n-1)) >> (n-1)

分析為什麼要》(n-1),相當於是我們4.2.4.5中的第二步

第二步,繼續解析剩下的:又分為2部分

x & ~(~(0u)<<(m-n+1))<<(n-1)

分析為什麼要&,相當於我們4.2.4.5中的第一步

第三步,繼續分析剩下的:

~(~(0u)<<(m-n+1))

<<(n-1) 

這個分析時要搞清楚第2坨到底應該先左邊取反再右邊《還是先右邊《再左邊取反。

解法:第一,查c語言優先順序表;第二,自己實際寫個**測試。

說明這個式子應該是~(~(0u)<<(m-n+1))

<<(n-1) ,這就又分為2部分了

10001000

00001110

00001000

太睏了,先睡覺去了~

C語言位操作

在電腦程式中,資料的位是可以操作的最小資料單位,理論上可以用 位運算 來 完成所有的運算和操作。一般的位操作是用來控制硬體的,或者做資料變換使用,但是,靈活的位操作可以有效地提高程式執行的效率。c語言提供了位運算的功 能,這使得c語言也能像組合語言一樣用來編寫系統程式。位運算子c語言提供了六種位運算...

c語言位操作

位運算 and與 有一位為0 運算就為0 想獲取高四位,a a 0xf0 簡寫 a 0xf0 清零 一三五七位清零 a a 0x55 檢測位 檢測第三位 a a 0x04 遮蔽高四位,保留低4 位 a a 0x0f 統計2進製a中1的個數 1 include2 int main 3 11 print...

C語言位操作

左移 右端補零,操作的物件是 任意 int char 這裡任意是指有無符號的意思。右移 無符號數或者是正數不用考慮是左端補0,負數看實現 一些實現補0,一些保留符號位,這種比較科學吧 按位取反 一元運算子 按位與 按位異或 按位或 為了保證可移植性,暫存器當然用unsinged char 或者uns...