web-dev-qa-db-fra.com

Comment retourner un bit spécifique dans un octet en C?

J'essaie d'utiliser des masques et de manipuler des bits spécifiques dans un octet. Par exemple:

Je veux écrire un programme en C qui retourne deux bits à des positions particulières, par exemple le bit en position 0 et celui en troisième position. Alors, 11100011, deviendrait 01110011.

Comment puis-je échanger ces bits?

21
Niels Robben

Le retournement d'un bit se fait en XOR-ing avec un masque: placez les bits aux positions que vous voulez retourner, puis exécutez un XOR, comme ceci:

int mask = 0x90; // 10010000
int num  = 0xE3; // 11100011
num ^= mask;     // 01110011

Voici quelques notes:

  1. les bits sont généralement comptés à partir de la position la moins significative, donc votre exemple retourne les bits aux positions 4 et 7, pas aux positions 0 et 4
  2. Pour construire un masque de bits pour une seule position, utilisez l'expression 1 << n, où n est le numéro de position compté à partir du bit le moins significatif.
  3. Pour combiner plusieurs bits dans un seul masque, utilisez | opérateur. Par exemple, (1 << 4) | (1 << 7) construit le masque pour retourner les bits 4 et 7.
27
dasblinkenlight

Si votre octet est x et que vous souhaitez commuter les bits aux i-ème et j-ème positions:

x = x ^ ((1<<i) | (1<<j));

Donc, dans votre cas, ce serait juste (1 << 4) | (1 << 7). :)

3
Eutherpy

Tout d'abord, bonne chance!

Une remarque - il est plus utile de compter les bits de droite et non de gauche, car il existe différentes tailles d'octets/mots (8 bits, 16 bits, etc.) et ce nombre préserve mieux la compatibilité. Donc, dans votre cas, vous faites référence aux bits # 7 et # 4 (zéro).

Vouliez-vous dire 'flip' (change 0 <-> 1 bits) ou 'switch' entre l'un et l'autre?

Pour la première option, la réponse ci-dessus (XOR avec "int mask = 0x90; // 10010000") est très bonne. Pour le second, c'est un peu plus délicat (mais pas beaucoup).

1
AssafR

Pour inverser les bits, vous pouvez utiliser l'exclusif OR opérateur au niveau du bit. Cela prend deux opérandes (généralement, la valeur sur laquelle vous souhaitez opérer et le masque définissant les bits à inverser). L'eXclusive = OR (XOR), l'opérateur ne retournera un peu que si, et seulement si, l'un des deux est défini sur 1, mais PAS les deux. Voir l'exemple (simple) ci-dessous:

#include <stdio.h>

int main(int argc, char** argv)
{
   int num = 7;   //00000111
   int mask = 3;  //00000011

   int result = num ^ mask; //00000100
   printf("result = %d\n", result); //should be 4

   return 0;
}
1