Opérations sur les bits en C++ : Comment définir, réinitialiser et basculer un seul bit (sans perdre la tête)
Bonjour, collègue ! Si tu as déjà regardé du code C++ écrit par quelqu'un d'autre et vu des symboles étranges comme |, & et ~, en te demandant « pourquoi font-ils ça ? » — tu es au bon endroit. Aujourd'hui, nous allons décortiquer l'un des sujets les plus populaires (et, honnêtement, les plus élégants) en programmation : les opérations sur les bits. Plus précisément, comment définir, réinitialiser et basculer un seul bit.
Ce n'est pas qu'un simple exercice académique. Travailler avec les bits est un super-pouvoir qui te sera utile partout : de la gestion des drapeaux de configuration et des périphériques de microcontrôleurs à l'optimisation du stockage de données dans les jeux ou les bases de données. Sur Stack Overflow, cette question a recueilli des centaines de milliers de vues — preuve qu'elle est vraiment importante.
Pas de théorie ennuyeuse — allons droit au but. C'est parti !
Pourquoi travaillons-nous avec les bits ?
Imagine que tu as 8 réglages différents (par exemple, activer le son, afficher les astuces, activer le mode nuit, etc.). Tu pourrais les stocker dans huit variables distinctes de type bool. Mais cela représenterait 8 octets (voire plus). Ou alors, tu peux utiliser un seul octet — 8 bits, chacun responsable d'un réglage. Une économie de mémoire de 8 fois — et ce n'est que le début.
Les opérations sur les bits sont une magie de bas niveau qui fonctionne incroyablement vite. Le processeur les exécute en un cycle. Pour les systèmes embarqués, les pilotes et les applications à forte charge, c'est crucial.
En C++, trois opérateurs principaux sont utilisés pour travailler avec les bits :
|(OU bit à bit) — pour définir un bit.&(ET bit à bit) — pour réinitialiser un bit.^(OU exclusif bit à bit, XOR) — pour basculer un bit.
Et un autre opérateur utile — ~ (NON bit à bit), qui inverse tous les bits. Il nous servira pour la réinitialisation.
Numérotation des bits : mettons-nous d'accord tout de suite
En programmation, les bits sont généralement numérotés à partir de zéro. Le bit de poids faible (Least Significant Bit, LSB) est le bit 0. Le bit de poids fort (Most Significant Bit, MSB) est le bit 7 pour un octet, 15 pour un mot (16 bits), etc.
Dans cet article, nous utiliserons uint8_t (entier non signé 8 bits) pour plus de clarté. Mais tous les exemples fonctionnent aussi avec int, unsigned int, uint32_t et tout autre type entier.
Comment définir un bit (Set bit)
Définir un bit signifie le mettre à 1, quelle que soit sa valeur précédente.
La méthode la plus simple consiste à utiliser le OU bit à bit avec un masque. Un masque est un nombre dans lequel seul le bit que nous voulons modifier est défini.
Formule :
nombre |= (1 << numéro_du_bit);Détaillons étape par étape :
1 << numéro_du_bit— on décale le 1 vers la gauche du nombre de positions souhaité. Si le numéro du bit est 3, alors1 << 3donne le binaire00001000.nombre | masque— l'opération OU mettra le bit à 1 s'il était à 0, et le laissera à 1 s'il était déjà à 1.
Exemple de code en C++ :
#include <iostream>#include <cstdint>
int main() { uint8_t flags = 0b00000000; // Initialement, tous les bits sont réinitialisés
// Définir le 3ème bit (en comptant à partir de zéro) flags |= (1 << 3);
// Maintenant flags = 0b00001000 std::cout << "Après la définition du bit 3 : " << static_cast<int>(flags) << std::endl;
// Définir le 0ème bit flags |= (1 << 0); // flags = 0b00001001 std::cout << "Après la définition du bit 0 : " << static_cast<int>