回覆列表
  • 1 # IT劉小虎

    1 個位元組(Byte)等於 8 個位(bit)似乎已經是程式設計師間的常識了,很少有人質疑這一點。但是作為C語言程式設計師,我們常常要在不同的硬體平臺上做底層開發,應該明白:1個位元組等於8個位只是慣例而已,C語言標準並沒有定義這一點。

    有些編譯器並不遵守這個慣例,例如,在 Texas 的 C55x DSP 的平臺上,1 個位元組等於 16 個位。在這個平臺上,各種資料型別佔用的位數有些奇怪:

    以 long long 為例,在該平臺上 long long 之所以等於 40 bit,而不是我們常用的 64 bit,是因為它們的 ALU 是 40 bit 寬,因此編譯器規定 long long 為 40 bit 可以降低功耗和提升效率。

    C語言操作位

    C語言沒有類似於 Java 的“垃圾回收”等高階程式語言特性,也不像 python 那樣無需顯示宣告型別就能使用變數,因此在很多人看來,C語言有些“低階”。但是C語言的這些“低階”也是 C語言的優點——使用C語言開發程式,程式設計師能夠準確知道究竟使用了多少資源,以及哪些資源還在記憶體裡,哪些已經被釋放。換句話說,C語言程式具備資源的使用確定性

    因此,C語言特別適合用於一些資源比較匱乏的專案開發中。在這些專案中,以嵌入式專案為代表,一般都需要嚴格控制記憶體的使用——使用 1 個位元組(Byte)就能存放的值,絕對不定義 2 個位元組寬度的變數。甚至,一些“摳門”的C語言程式設計師會將 1 個位元組掰成若干個位(bit)使用。

    所以,在C語言程式開發中,常常需要操作某個變數特定的位(bit),這對於C語言來說當然沒有任何難度,各種移位操作就能夠方便的解決該類需求,例如:

    上面第二行C語言程式碼將 status 的第3個位(bit 2)設定為 1,第三行C語言程式碼將 status 的第1個位(bit 0)設定為 0。可以看出,藉助於位運算,C語言可以比較簡單的操作 status 的指定位。不過,C語言這種操作位的方法有時候看起來不夠直觀——至少沒有直接賦值那麼直觀。

    那C語言有沒有更加直觀的位操作方法呢?

    上面的例子透過移位、以及或與非等操作實現對變數 status 的位操作,但是看起來卻不是那麼直觀,那麼C語言有沒有更加直觀的位操作方法呢?似乎可以藉助C語言的聯合體(union)和位域(bit field)語法,間接的實現位操作,請看下面的C語言程式碼:

    此例中 status 和 bits 結構體共享一個位元組的記憶體空間,結構體 bits 利用C言中的位域語法將一個位元組的記憶體空間拆分成 8 個位,這種情況下,要讀寫 status 的位就非常簡單了,請看下面的C語言示例程式碼:

    編寫 main() 函式,測試透過位域操作 status 的位,相關C語言程式碼如下,請看:

    main() 函式一開始將 status 置為 0,然後將它的 bit1 和 bit3 設定為 1,也就相當於將 status 設定為 0x0a,編譯並執行這段C語言程式碼,得到如下輸出:

    一切與預期一致,這樣就實現了以“賦值”的形式,操作C語言中的位,而且看起來比“移位與或非操作”更加直觀,所以這樣的操作更好了?

    自然要看情況,比如在開頭提到的幾種已經平臺上,上述C語言程式碼就不再適用了,另外, 就算在 1 個位元組等於 8 個位的硬體平臺上,單個位元組的 8 個位是如何分佈的也是沒有明確標準的。這就導致上面這種基於位域的操作位的方法不具備可移植性。

    不過,這種方法又的確可以帶來一些方便,具體取捨由題主決定了。

  • 2 # Gfilsxin

    一個位元組一定是8個位元位!

    C語言中操作某個位,主要用到以下運算子:

    “位與”:&“位或”:|“左移右移”:<<,>>“位取反”:~

    如果想把第n個位元位清零,可執行如下程式碼:

    char data;data &= ~(1<<n);

    如果想把第n個位元位置1,可執行如下程式碼:

    char data;data |= 1<<n;
  • 3 # Code每分鐘

    一個位元組肯定是8位元,人家就是這麼定義的,位操作不推薦用位域,採用位運算子最好,為什麼?因為可移植性,記憶體對齊

  • 中秋節和大豐收的關聯?
  • 如果巴特勒本賽季復出,加上羅斯、唐斯、蒂格和維金斯,能在西部突圍嗎?