Dal momento che nessuno ha affrontato l'argomento del perché questi sono utili:
Uso molto le operazioni bit per bit quando lavoro con le bandiere. Ad esempio, se si desidera passare una serie di flag a un'operazione (ad esempio File.Open()
, con la modalità di lettura e la modalità di scrittura entrambe abilitate), è possibile passarli come un singolo valore. Ciò si ottiene assegnando ad ogni possibile flag il proprio bit in un bitset (byte, short, int o long). Per esempio:
Read: 00000001
Write: 00000010
Quindi, se si desidera passare in lettura e scrittura, si passerà (READ | WRITE) che quindi combina i due in
00000011
Che poi può essere decifrato dall'altra parte come:
if ((flag & Read) != 0) { //...
che controlla
00000011 &
00000001
che ritorna
00000001
che non è 0, quindi il flag specifica READ.
Puoi usare XOR per attivare o disattivare vari bit. L'ho usato quando ho usato una bandiera per specificare input direzionali (Su, Giù, Sinistra, Destra). Ad esempio, se uno sprite si muove in orizzontale e voglio che si giri:
Up: 00000001
Down: 00000010
Left: 00000100
Right: 00001000
Current: 00000100
Ho semplicemente XOR il valore corrente con (SINISTRA | DESTRA) che disattiva SINISTRA e DESTRA, in questo caso.
Bit Shifting è utile in diversi casi.
x << y
equivale a
x * 2 y
se devi moltiplicare rapidamente per una potenza di due, ma fai attenzione a spostare un 1 bit nel bit superiore - questo rende il numero negativo a meno che non sia senza segno. È anche utile quando si ha a che fare con dati di dimensioni diverse. Ad esempio, leggendo un numero intero da quattro byte:
int val = (A << 24) | (B << 16) | (C << 8) | D;
Supponendo che A sia il byte più significativo e D il minimo. Sarebbe finito come:
A = 01000000
B = 00000101
C = 00101011
D = 11100011
val = 01000000 00000101 00101011 11100011
I colori vengono spesso memorizzati in questo modo (con il byte più significativo ignorato o utilizzato come Alpha):
A = 255 = 11111111
R = 21 = 00010101
G = 255 = 11111111
B = 0 = 00000000
Color = 11111111 00010101 11111111 00000000
Per trovare nuovamente i valori, basta spostare i bit verso destra fino a quando non è in fondo, quindi mascherare i rimanenti bit di ordine superiore:
Int Alpha = Color >> 24
Int Red = Color >> 16 & 0xFF
Int Green = Color >> 8 & 0xFF
Int Blue = Color & 0xFF
0xFF
è lo stesso di 11111111
. Quindi essenzialmente, per Red, faresti questo:
Color >> 16 = (filled in 00000000 00000000)11111111 00010101 (removed 11111111 00000000)
00000000 00000000 11111111 00010101 &
00000000 00000000 00000000 11111111 =
00000000 00000000 00000000 00010101 (The original value)