ProgrammationDéveloppeur Système/C++

Parlez des différences entre les mots-clés 'mutable', 'volatile' et 'const' en C++. À quoi servent-ils, quelles erreurs typiques surviennent lors de leur utilisation incorrecte ?

Réussissez les entretiens avec l'assistant IA Hintsage

Réponse

const indique au compilateur qu'une variable est immuable (ne peut pas être modifiée après l'initialisation). Utilisé pour déclarer des variables constantes, ainsi que pour des méthodes qui ne modifient pas l'état de l'objet.

mutable permet de modifier la valeur d'un champ de classe même à l'intérieur de méthodes const.

volatile indique au compilateur que la valeur d'une variable peut être modifiée en dehors du contrôle du programme (par exemple, par le matériel), et le compilateur ne doit pas optimiser les accès à celle-ci.

Exemple de code

class Logger { public: void log() const { ++count; // Acceptable — count est déclaré mutable } private: mutable int count = 0; }; volatile int flag; void wait() { while (flag == 0) { /* le compilateur n'optimise pas la boucle, car flag est volatile */ } }

Question piège

« Que se passe-t-il si on déclare un membre de classe à la fois comme const et mutable ? »

Réponse : Cela n'est pas possible, ce sont des qualifications incompatibles ; le compilateur générera une erreur.


Exemples réels d'erreurs dues à un manque de connaissance sur le sujet.


Histoire

Dans un logiciel industriel pour travailler avec du matériel, le développeur a déclaré des données, mises à jour par des interruptions externes, comme des int ordinaires. L'optimisation du compilateur a supprimé les lectures répétées de ces variables, ce qui a fait que le programme "s'est bloqué" dans une boucle infinie. Le problème n'a pu être diagnostiqué qu'après avoir remplacé par volatile int.


Histoire

Une des classes de journalisation avait une méthode log() const, où il était nécessaire de mettre à jour le compteur d'appels. Au départ, cela était fait via un pointeur const_cast, ce qui a provoqué de nombreux avertissements et des bogues peu évidents. Le problème a disparu après avoir correctement déclaré le compteur avec mutable.


Histoire

Certains méthodes de la classe étaient déclarées comme const, mais des membres de type pointeur étaient modifiés (par exemple, pour la mise en cache). Cela a conduit à une violation de la logique de "const-correctness" et même à des UB, si l'objet était réellement placé dans une zone en lecture seule. Il aurait fallu utiliser mutable ou modifier la conception.