Il linguaggio C++ mette a disposizione un insieme di operatori specializzati nella manipolazione dei bit di variabili di tipo intero, detti operatori bit a bit (o bitwise).
L'uso di questi operatori è solitamente relegato a contesti in cui l'ottimizzazione nella gestione delle risorse quali memoria e cicli di processore ha netta prevalenza sulla leggibilità e manutenibilità del codice.
Per questo motivo, il loro utilizzo non è tra le caratteristiche desiderabili di un codifica basata sui paradigmi di programmazione più moderni e avanzati. Tuttavia, a parte che per ragioni di retrocompatibilità con C, essi sono parte della specifica del linguaggio e trovano spesso applicazione nella programmazione dei moderni microcontrollori, in cui la gestione delle risorse può essere un fattore determinante per l'operabilità.
Nella tabella seguente si trova un elenco degli operatori bit a bit:
Operatore | Simbolo | Sintassi | Effetto | Esempio |
---|---|---|---|---|
NOT bit a bit | ~ | ~x | Inverte tutti i bit della variable x | ~ 0011 = 1100 |
AND bit a bit | & | x & y | Effettua lo AND bit a bit tra x e y | 1101 & 0111 = 0101 |
OR bit a bit | | | x | y | Effettua lo OR bit a bit tra x e y | 1011 | 0101 = 1111 |
XOR bit a bit | ^ | x ^ y | Effettua lo XOR bit a bit tra x e y | 1011 | 0101 = 1110 |
Spostamento a destra | >> | x >> y | Sposta i bit di x a destra di y posizioni | 1011 >> 1 = 0101 |
Spostamento a sinistra | << | x << y | Sposta i bit di x a sinistra di y posizioni | 1011 << 1 = 0110 |
Si osservi che l'applicabilità di tali operatori è relegata alla manipolazione di variabili intere e prive di segno.
Lo standard C++ infatti non specifica la modalità di rappresentazione degli interi con segno (solitamente in complemento a 2) e nemmeno la modalità di spostamento (aritmetico o logico).
Questi dettagli implementativi sono tipicamente demandati ai compilatori delle singole piattaforme, e pertanto l'applicazione degli operatori bit a bit su variabili intere con segno potrebbe generare problemi di portabilità.
Inoltre, essi non sono definiti per i tipi double
e float
, poichè la loro rappresentazione interna suddivisa in mantissa, esponente e segno renderebbe di poca utilità una manipolazione bit a bit.
È importante inoltre sottolineare la differenza tra operatori booleani AND, OR e NOT e gli omologhi operatori bit a bit. Da un punto di vista concettuale, infatti, i risultati da essi prodotti corrispondono soltanto se applicati su bit singoli.
Infine, nella tabella seguente sono elencati gli operatori di assegnamento bit a bit, che consentono di condensare un'operazione bit a bit tra due operandi e l'assegnamento del risultato in un'unica istruzione:
Operatore | Simbolo | Sintassi | Effetto |
---|---|---|---|
AND= bit a bit | &= | x &= y | Effettua lo AND bit a bit tra x e y e assegna il risultato a x |
OR= bit a bit | |= | x |= y | Effettua lo OR bit a bit tra x e y e assegna il risultato a x |
XOR= bit a bit | ^= | x ^= y | Effettua lo XOR bit a bit tra x e y e assegna il risultato a x |
Assegnamento con spostamento a destra | >>= | x >>= y | Sposta i bit di x a destra di y posizioni e assegna il risultato a x |
Assegnamento con spostamento a sinistra | <<= | x <<= y | Sposta i bit di x a sinistra di y posizioni e assegna il risultato a x |
L'utilizzo prevalente delle opearazioni bit a bit consiste nella manipolazione di variabili il cui stato binario viene usato per rappresentare molteplici flag mediante l'associazione ai singoli bit di un'unica entità referenziabile.