39

低レベルのビット操作は、私の得意分野ではありません。次のビット単位演算子の使用例を理解する上で、いくつかの助けをいただければ幸いです。考慮してください...

int age, gender, height, packed_info;

. . .   // Assign values 

// Pack as AAAAAAA G HHHHHHH using shifts and "or"
packed_info = (age << 8) | (gender << 7) | height;

// Unpack with shifts and masking using "and"
height = packed_info & 0x7F;   // This constant is binary ...01111111
gender = (packed_info >> 7) & 1;
age    = (packed_info >> 8);

このコードが何をどのように達成しているのかわかりません。マジック ナンバー 0x7F を使用する理由 梱包と開梱はどのように行われますか?

ソース

4

7 に答える 7

13

これはビット操作のかなり長いレッスンになる可能性がありますが、最初にウィキペディアのビット マスキングの記事を紹介させてください。

packed_info = (age << 8) | (gender << 7) | height;

年齢を取り、その値を 8 ビットで移動し、次に性別を取り、それを 7 ビットで移動すると、身長が最後のビットを占有します。

age    = 0b101
gender = 0b1
height = 0b1100
packed_info = 0b10100000000
            | 0b00010000000
            | 0b00000001100
/* which is */
packed_info = 0b10110001100

アンパックは逆を行いますが、0x7F (0b 01111111) のようなマスクを使用して、フィールド内の他の値を削除します。

gender = (packed_info >> 7) & 1;

次のように動作します...

gender = 0b1011 /* shifted 7 here but still has age on the other side */
       & 0b0001
/* which is */
gender = 0b1

何かを 1 に AND することはそのビットを「保持する」ことと同じであり、0 と AND をとることはそのビットを「無視する」ことと同じであることに注意してください。

于 2011-07-02T12:33:57.167 に答える
2

私が何度も直面したのと同じ要件。Bitwise AND 演算子を使えばとても簡単です。値を 2 の累乗で修飾するだけです(2)。複数の値を格納するには、それらの相対数 (2 の累乗) を加算して SUM を取得します。この SUM は、選択した値を統合します。どうやって ?

すべての値でビット単位の AND を実行するだけで、選択されていない値にはゼロ (0) が返され、選択されている値にはゼロ以外が返されます。

説明は次のとおりです。

1) 値 (YES、NO、MAYBE)

2) 2 の累乗への代入 (2)

YES   =    2^0    =    1    =    00000001
NO    =    2^1    =    2    = 00000010
MAYBE =    2^2    =    4    = 00000100

3) 私は YES を選択し、MAYBE を選択したため、合計:

SUM    =    1    +    4    =    5

SUM    =    00000001    +    00000100    =    00000101 

この値には、YES と MAYBE の両方が格納されます。どうやって?

1    &    5    =    1    ( non zero )

2    &    5    =    0    ( zero )

4    &    5    =    4    ( non zero )

したがって、SUM は

1    =    2^0    =    YES
4    =    2^2    =    MAYBE.

より詳細な説明と実装については、私のブログをご覧ください

于 2018-01-19T16:08:04.047 に答える