Manipulations de bit

Un excellent exemple des capacités de D à générer du code à la compilation avec des mixins est celui de la manipulation de bits.

Manipulations simples

D implémente les opérateurs suivants pour manipuler des bits:

  • & et bit à bit
  • | ou bit à bit
  • ~ inversion bit à bit
  • << décallage à gauche signé bit à bit
  • >> décallage à droite signé bit à bit
  • >>> décallage à droite non-signé bit à bit

Exemple

Une manipulation bit à bit courante est de lire la valeur d'un bit. core.bitopt.bt est suffisant pour les tâches les plus communes, mais pour s'habituer à la manipulation bit à bit, implémentons la lecture d'un bit de manière un peu verbeuse:

enum posA = 1;
enum maskA = (1 << posA);

bool getFieldA()
{
    return _data & maskA;
}

Une généralisation de cette fonction consiste à tester des blocs plus grand que 1, et donc de créer un masque de lecture avec la longueur nécessaire, puis de décaller les données et d'appliquer le masque:

enum posA = 1;
enum lenA = 3;
enum maskA = (1 << lenA) - 1; // ...0111

uint getFieldA()
{
    return (_data >> posA) & maskA;
}

On peut modifier la valeur d'un bit en inversant le masque et en autorisant donc l'écriture que dans le bloc spécifié:

void setFieldA(bool b)
{
    return (_data & ~maskAWrite) | ((b << aPos) & maskAWrite),
}

std.bitmanip à la rescousse !

C'est très amusant d'écrire son propre code pour faire de la manipulation bit à bit et D fournit tous les outils nécessaires pour le faire. Mais dans la plupart des cas, on ne veut pas copier-coller ce code de manipulation, car c'est sujet à erreurs et difficile à maintenir. D vous permet donc d'écrire des manipulations bit à bit lisibles et maintenables avec std.bitmanip et la puissance des mixins, sans sacrifier les performances.

Jetez un coup d'œil à votre droite. Un BitVector est défini, mais il n'utilise que X bits et il est totalement indistinguable d'une structure normale

std.bitmanip et core.bitop contiennent plein d'autres outils qui sont d'une grande aide pour écrire des applications qui ont besoin d'économiser leur mémoire.

padding et alignement

Comme le compilateur va ajouter du padding (remplissage) aux variables de taille inférieure à la taille de la mémoire dans le système d'exploitation (size_t.sizeof), par exemple bool, byte, char, il est recommandé de commencer avec des champs de haut alignement.

Pour aller plus loin

rdmd playground.d