55 votes

Que sont les qualificatifs const de premier niveau ?

Qu'est-ce que const au qualificatif "top level" signifie en C++ ?

Et quels sont les autres niveaux ?

Par exemple :

int const *i;
int *const i;
int const *const i;

0 votes

Je ne sais pas ce que vous entendez par exemples mais j'ai ajouté quelques qualificatifs de const que je connais.

62voto

James Kanze Points 96599

Un qualificatif const de haut niveau affecte l'objet lui-même. Les autres ne sont pertinents avec les pointeurs et les références. Ils ne rendent pas l'objet const, et empêchent seulement la modification par un chemin utilisant le pointeur ou la référence. référence. Ainsi :

char x;
char const* p = &x;

Il ne s'agit pas d'une const de haut niveau, et aucun des objets n'est immuable. L'expression *p ne peut pas être utilisé pour modifier x mais d'autres expressions peuvent être ; x n'est pas constant. D'ailleurs

*const_cast<char*>( p ) = 't'

est légal et bien défini.

Mais

char const x = 't';
char const* p = &x;

Cette fois, il y a une constance de haut niveau sur x donc x est immuable. Non expression n'est autorisée à le modifier (même si const_cast est utilisé). Le compilateur compilateur peut mettre x dans la mémoire morte, et il peut supposer que la x ne change jamais, indépendamment de ce que peut faire un autre code.

Pour donner au pointeur un niveau supérieur const vous écrivez :

char x = 't';
char *const p = &x;

Dans ce cas, p pointera vers x pour toujours ; toute tentative de changer ceci est un comportement non défini (et le compilateur peut mettre p dans la mémoire morte, ou supposez que *p se réfère à x indépendamment de tout autre code).

9 votes

Un autre point : lors de l'écriture de fonctions, les qualificatifs de premier niveau des arguments sont ignorés. Cela signifie que void foo(char const) y void foo(char) ont la même fonction (et en fait, elles peuvent être interchangées). Le raisonnement est que puisque l'argument est pris par copie, l'appelant ne se soucie pas de savoir si la copie peut être modifiée ou non, donc c'est transparent pour lui.

8 votes

@MatthieuM. Bon point, même si ce n'est pas tout à fait vrai comme indiqué. Les qualificatifs de haut niveau sont ignorés dans une déclaration, et dans le type de la fonction. Dans la définition, cependant, ils se comportent comme d'habitude dans la fonction. (Les qualificatifs de premier niveau sont également ignorés par les fonctions typeid et les paramètres des modèles, lors de la sélection des exceptions à attraper, et probablement dans d'autres cas que j'ai oubliés. En pratique, ils n'ont pas non plus d'effet sur les valeurs de retour de type non-classe).

0 votes

En ce qui concerne le dernier exemple avec const p : p=0; est une tentative de changer p mais il n'a pas un comportement indéfini, il est juste mal formé.

13voto

Blagovest Buyukliev Points 22767

int *const i met const au niveau supérieur, alors que int const *i ne le fait pas.

La première dit que le pointeur i est lui-même immuable, tandis que la seconde dit que la mémoire vers laquelle pointe le pointeur est immuable.

Chaque fois que const apparaît immédiatement avant ou après le type de l'identifiant, qui est considéré comme un qualificatif de premier niveau.

1 votes

Réponse excellente et claire. P.S. int const *i est égal à const int *i (toutes sont des constantes de bas niveau). J'utilise const int *i (de bas niveau) pour distinguer plus souvent son niveau const de int *const i (niveau supérieur).

0 votes

J'ai du mal à comprendre "Chaque fois que const apparaît immédiatement avant ou après le type de l'identifiant, cela est considéré comme un qualificatif de haut niveau." Cela ne s'applique-t-il pas à int const *i parce que le const apparaît au milieu du type de l'identifiant, qui est dans ce cas-ci int * ?

13voto

Glenn Teitelbaum Points 3564

La façon dont on me l'a expliqué, donné :

[const] TYPE * [const] VARIABLE

VARIABLE est utilisé pour pointer vers données de type TYPE par le biais de *VARIABLE

Tracez une ligne à travers le * ou multiples * s

  1. S'il existe un const à la gauche de la * il s'applique à la données et le données ne peut être modifié : *VARIABLE ne peuvent être attribuées, sauf lors de l'initialisation
  2. S'il existe un const à la droite de la * il s'applique à la VARIABLE et ce que le VARIABLE ne peut être modifié : VARIABLE ne peuvent être attribuées, sauf lors de l'initialisation

Donc :

          |              left  right
int       *       i1;
          |              no    no     can change *i1 and i1

int const *       i2;     
          |              yes   no     cannot change *i2 but can change i2

int       * const i3;
          |              no    yes    can change *i3 but i3 cannot be changed

int const * const i4;
          |              yes   yes    cannot change *i4 or i4

13voto

Aditya Raj Points 147

Les deux niveaux de const sont : * Const de bas niveau * Const de haut niveau

Vous devez examiner les constantes de haut et de bas niveau à travers les références et les pointeurs, car c'est là qu'elles sont pertinentes.

int i = 0;
int *p = &i;
int *const cp = &i;
const int *pc = &i;
const int *const cpc = &i;

Dans le code ci-dessus, il y a 4 déclarations de pointeurs différentes. Passons en revue chacune d'entre elles,

int *p : Pointeur normal peuvent être utilisés pour apporter des modifications à l'objet sous-jacent et peuvent être réaffectés.

int *const cp (const de haut niveau) : Const Pointer peut être utilisé pour apporter des modifications à l'objet sous-jacent mais ne peut pas être réaffecté. (Impossible de le modifier pour qu'il pointe vers un autre objet).

const int *pc (const de bas niveau) : Pointeur vers Const ne peut pas être utilisé pour apporter des modifications à l'objet sous-jacent mais peut lui-même être réaffecté.

const int *const cpc (tant au niveau supérieur qu'au niveau inférieur) : Const Pointeur vers une Const ne peut ni être utilisé pour apporter des modifications à l'objet sous-jacent, ni être lui-même réaffecté.

De plus, le const de haut niveau est toujours ignoré lorsqu'il est assigné à un autre objet, alors que le const de bas niveau n'est pas ignoré.

int i = 0;
const int *pc = &i;
int *const cp = &i;

int *p1 = cp; // allowed
int *p2 = pc; // error, pc has type const int*

J'espère que cela vous a aidé :) FYI : C++ Primer a beaucoup d'informations sur le même sujet !!!

Prograide.com

Prograide est une communauté de développeurs qui cherche à élargir la connaissance de la programmation au-delà de l'anglais.
Pour cela nous avons les plus grands doutes résolus en français et vous pouvez aussi poser vos propres questions ou résoudre celles des autres.

Powered by:

X