Opérateur de décalage de bits en C++

Anam Javed 12 octobre 2023
  1. Opérateur de décalage de bit vers la gauche en C++
  2. Opérateur de décalage de bits à droite en C++
  3. Décalage de bits sur le type de données flottant en C++
  4. Décalage de bits dans un tableau en C++
  5. Bit Shift et Mask en C++
  6. Décalage de bits pour les nombres négatifs en C++
  7. Décalage de bits à l’aide de Long en C++
  8. Conclusion
Opérateur de décalage de bits en C++

En C++, les opérateurs de décalage de bits font ce que leurs noms suggèrent, en décalant des bits. Selon les exigences du programme, un opérateur de décalage au niveau du bit décale les bits binaires vers la gauche ou vers la droite.

Des valeurs entières sont appliquées à ces opérateurs (int, long, éventuellement court et byte ou char). Dans certains langages, l’utilisation des opérateurs de décalage sur tout type de données inférieur à int redimensionne automatiquement l’opérande en int.

Cet article traite en détail des opérateurs de décalage gauche et droit en C++ et de leur implémentation, ainsi que d’exemples pertinents.

Opérateur de décalage de bit vers la gauche en C++

L’opérateur de décalage à gauche décale les bits dans l’expression de décalage vers la gauche du nombre de places dans l’expression additive. Les positions de bit libérées par l’opération de décalage sont remplies de zéros et les bits décalés à la fin sont ignorés, y compris le bit de signe.

L’opérateur de décalage à gauche prend deux nombres. Cela décale les bits du premier opérande et le deuxième opérande décide du nombre de positions à décaler.

On peut dire que décaler à gauche un entier a par un entier b, noté (a<<b), équivaut à multiplier a par 2^b (2 élevé à la puissance b). L’opérateur de décalage vers la gauche est noté <<.

Par exemple, M<<k. Ici, M est le premier opérande et k est le deuxième opérande.

Prenons M=33; qui vaut 100001 en binaire et k = 2. Si M est décalé à gauche de 2, noté M=M<<2, il deviendra M=M(2^2).

Ainsi, M=33(2^2)=132 peut s’écrire 10000100.

Exemple:

#include <iostream>
using namespace std;

int main() {
  unsigned char x = 6, y = 7;
  cout << "x<<1 = " << (x << 1) << endl;
  cout << "y<<1 = " << (y << 1) << endl;
  return 0;
}

Production:

x<<1 = 12
y<<1 = 14

Dans le code ci-dessus, les variables non signées char x et char y désignent un type de données de caractère dans lequel la variable utilise tous les 8 bits de la mémoire, et il n’y a pas de bit de signe (qui est là en caractère signé).

Ici, char x est égal à 6, soit 00000110 en binaire, et char y est égal à 7, soit 00000111 en binaire.

La première instruction d’impression indique de décaler à gauche la valeur de x de 1 bit ; le résultat est 00001100. La deuxième instruction d’impression indique de décaler à gauche la valeur de y de 1 bit ; le résultat est 00001110.

Opérateur de décalage de bits à droite en C++

L’opérateur de décalage vers la droite décale la configuration binaire dans l’expression de décalage du nombre de places que l’expression additive fournit vers la droite. Les emplacements de bits libérés par l’opération de décalage sont remplis de zéros pour les valeurs non signées.

Le bit de signe remplace les emplacements de bit vacants dans les nombres signés. Si le nombre est positif, la valeur 0 est utilisée ; si le nombre est négatif, la valeur 1 est utilisée.

L’opérateur de décalage à droite prend deux nombres. Cela décale les bits du premier opérande et le deuxième opérande décide du nombre de positions à décaler.

On peut dire que décaler à droite un entier a par un entier b, noté (a>>b), équivaut à diviser a par 2^b (2 élevé à la puissance b). L’opérateur de décalage vers la droite est noté : >>.

Par exemple, M>>k . Ici, M est le premier opérande et k est le second.

Prenons M=32; qui vaut 100000 en binaire et k = 2. Si M est décalé vers la droite de 2, noté M=M>>2, alors M deviendra M=M/(2^2). Ainsi, M=32/(2^2)=8 peut s’écrire 1000.

Exemple de programme :

#include <iostream>

int main() {
  unsigned char x = 6, y = 9;
  cout << "a>>1 = " << (a >> 1) << endl;
  cout << "b>>1 = " << (b >> 1) << endl;
  return 0;
}

Production:

x>>1 = 3
y>>1 = 4

Dans le code ci-dessus, les variables non signées char x et char y désignent un type de données de caractère dans la variable qui utilise tous les 8 bits de la mémoire, et il n’y a pas de bit de signe (qui est là en caractère signé).

Ici, char x est égal à 6, soit 00000110 en binaire, et char y est égal à 9, soit 00001001 en binaire.

La première instruction d’impression indique de décaler vers la droite la valeur de x de 1 bit ; le résultat est 00000011. La deuxième instruction d’impression indique de décaler à droite la valeur de y de 1 bit ; le résultat est 00000100.

Décalage de bits sur le type de données flottant en C++

Vous ne pouvez pas décaler un flottant en C++ car il affichera une erreur, mais pourquoi ? C’est parce que les flottants sont stockés dans un format spécial.

32 bits pour un flottant sont divisés en deux catégories : un signifiant et un exposant. Un décalage peut potentiellement décaler des bits de la catégorie des exposants vers la catégorie des signifiants ou vice versa.

Exemple:

#include <stdio.h>

int main(int ar, char *arg[]) {
  float testFl = 2.5;

  printf("testFloat (before): %f\n", testFl);
  testFl = testFl << 1;
  printf("testFloat (after): %f\n", testFl);
  return 0;
}

Production:

error: invalid operands to binary << (have 'float' and 'int')

Le décalage à droite ou à gauche effondrerait tous les bits.

Décalage de bits dans un tableau en C++

Il existe un tableau ar[] de taille n et un entier m.

Le but est de rendre tous les éléments du tableau > m en effectuant des opérations de décalage vers la droite sur tous les éléments du tableau présents. Si vous n’êtes pas en mesure de le faire, imprimez -1.

Exemple:

Input: ar[] = { 21, 22, 23, 19 }, m = 34
Output: { 26, 26, 27, 25 }

Explanation:
ar[0] = 10101
After 1 right shift, 11010 → 26
ar[1] = 10110
After 3 right shift, 11010 → 26
ar[2] = 10111
After  1 right shift, 11011 → 27
ar[3] = 10011
After 2 right shift, 11001 → 25

Code:

#include <bits/stdc++.h>
using namespace std;

int setBitNumber(int n) {
  int m = log2(n);
  return m;
}

bool check(int ar[], int m, int n) {
  for (int i = 0; i < n; i++) {
    if (ar[i] <= m) return false;
  }
  return true;
}

void modifyArray(int ar[], int m, int n) {
  for (int i = 0; i < n; i++) {
    if (ar[i] > m)
      continue;
    else {
      int bits = setBitNumber(ar[i]);
      int el = ar[i];
      for (int j = 0; j < bits; j++) {
        if (el & 1) {
          el >>= 1;
          el |= (1 << bits);
        } else {
          el >>= 1;
        }
        if (el > m) {
          arr[i] = el;
          break;
        }
      }
    }
  }

  if (check(ar, m, n)) {
    for (int i = 0; i < n; i++) cout << ar[i] << " ";
  } else
    cout << -1;
}

int main() {
  int ar[] = {21, 22, 23, 19};
  int n = sizeof(ar) / sizeof(ar[0]);
  int m = 24;
  modifyArray(ar, m, n);
  return 0;
}

Production:

[26, 26, 27, 25]

L’opération principale effectuée dans le programme est le parcours du tableau. Il effectue l’opération de décalage à droite sur chaque élément du tableau ar[i].

La condition est vérifiée si ar[i] > m. Si c’est vrai, alors mettez à jour le tableau ar[i], sinon continuez.

Si un élément du tableau ar[i] ≤ m, alors imprimez -1, sinon imprimez le tableau ar[i].

Bit Shift et Mask en C++

Un masque spécifie quels bits doivent être conservés et lesquels doivent être effacés.

Exemple:

Mask:   00001111b
Value:  01010101b

Lorsque nous appliquons le masque sur la valeur, nous souhaitons effacer les quatre premiers bits (supérieurs) tout en conservant les quatre derniers bits (inférieurs). En conséquence, nous avons récupéré les quatre derniers bits.

Production:

Mask:   00001111b
Value:  01010101b
Result: 00000101b

Les opérateurs de décalage de bits sont fréquemment utilisés avec des opérations de masquage pour décoller les bits d’un nombre un par un. L’exemple suivant explique comment diviser un caractère non signé en un tableau de bits séparés.

unsigned char y = 0xD5;
unsigned char bit[8];
unsigned char mask = 1;
for (int x = 7; x >= 0; x--) {
  bits[x] = y & mask;
  y = y >> 1;
}

Décalage de bits pour les nombres négatifs en C++

Les nombres négatifs ne doivent pas être saisis à l’aide des opérateurs de décalage gauche et droit. Si l’un ou l’autre des opérandes est un entier négatif, le résultat est un comportement indéfini.

Par exemple, le résultat de 1 >> -1 et de 1 << -1 est indéfini.

#include <iostream>

int main() {
  unsigned char x = -6, cout << "a>>1 = " << (a >> 1) << endl;
  return 0;
}

Production:

error: undefined behavior in C

Décalage de bits à l’aide de Long en C++

Le type de données long est utilisé pour décaler les bits de 32 ou 64 bits.

Exemple:

Pour 32 bits,

unsigned long A = (1L << 37)

Pour 64 bits,

unsigned long long A = (1ULL << 37);

Pour implémenter ce qui suit à l’aide d’un programme :

#include <stdio.h>

int main(void) {
  long long y = 1ULL;

  // Left shift 40 times
  y <<= 20;
  y <<= 20;

  printf("y is %lld\n", y);
  return 0;
}

Production:

y is 1099511627776

Ici, une variable 64 bits long long y est prise, et 1ULL est une constante long long int non signée (64 bits). La variable y est décalée 40 fois et s’imprime.

Conclusion

Dans cet article, nous avons discuté de l’opérateur de décalage de bits en C++. Nous avons appris en détail les opérateurs de décalage gauche et droit en C++.

Article connexe - C++ Operator