143 votes

const statique

const static int foo = 42;

J'ai vu cela dans un peu de code ici à StackOverflow et je ne pouvais pas comprendre ce qu'il fait. Puis j'ai vu quelques confus answeres dans d'autres forums. Ma meilleure supposition est que c'est utilisé en C pour cacher la constante de foo à partir des autres modules. Est-ce correct? Si oui, pourquoi serait-on l'utiliser en C++ contexte où vous pouvez simplement vous rendre private?

243voto

Motti Points 32921

Beaucoup de gens ont donné la réponse basique, mais personne ne l'a souligné qu' const par défaut est static (et certains ont donné de fausses informations). Voir le C++98 standard de la section 3.5.3.

Tout d'abord quelques informations:

L'unité de traduction: Un fichier source après le pré-compilateur (de manière récursive) inclus l'ensemble de ses fichiers à inclure.

Une liaison statique: Un symbole est uniquement disponible au sein de son unité de traduction.

Liaison externe: Un symbole est disponible à partir d'autres unités de traduction.

En namespace niveau

Cela comprend l'espace de noms global aka variables globales

static const int sci = 0; // sci is explicitly static
const int ci = 1;         // ci is implicitly static
extern const int eci = 2; // eci is explicitly extern
extern int ei = 3;        // ei is explicitly extern
int i = 4;                // i is implicitly extern
static int si = 5;        // si is explicitly static

Au niveau de la fonction

static signifie que la valeur est maintenue entre les appels de fonction.
La sémantique de la fonction static variables est similaire pour les variables globales qu'ils résident dans le programme les données de segment (et pas la pile ou le tas), voir à cette question pour plus de détails sur static "variables de durée de vie.

En class niveau

static signifie que la valeur est partagée entre toutes les instances de la classe et de l' const signifie qu'il ne change pas (et peut être initialisé inline) c'est le seul cas dans lequel ni l' static ni l' const sont redondantes.

131voto

Chris Arguin Points 6469

Il a utilise à la fois le C et le C++.

Comme vous l'avez deviné, la partie "statique" des limites de son champ d'application pour que l' unité de compilation. Il prévoit également initialisation statique. "const" indique au compilateur de ne pas laisser quelqu'un de le modifier. Cette variable est alors mis sur les données ou le segment bss en fonction de l'architecture, et peut-être dans la mémoire à lecture seule.

Tout ce qui est de savoir comment C traite ces variables ( ou comment C++ traite de noms de variables ). En C++, un membre marquée statique est partagée par toutes les instances d'une classe donnée. Si c'est privé ou pas n'influe pas sur le fait qu'une variable est partagée par plusieurs instances. Ayant 'const' il vous avertira si aucun code d'essayer de le modifier.

Si elle était strictement privé, puis chaque instance de la classe serait d'obtenir sa propre version ( optimiseur nonobstant)

45voto

Richard Corden Points 12292

Cette ligne de code peut effectivement apparaître dans plusieurs contextes différents et alghough il se comporte approximativement la même, il existe de petites différences.

Espace De Noms De Champ

// foo.h
static const int i = 0;

'i"sera visible dans chaque unité de traduction qui comprend l'en-tête. Cependant, à moins que vous avez fait d'utiliser l'adresse de l'objet (par exemple. '&i'), Je suis assez sûr que le compilateur va traiter 'i"simplement comme un type de coffre-fort 0. Lorsque deux ou plus d'unités de traduction prendre le '&i', puis l'adresse sera différent pour chaque unité de traduction.

// foo.cc
static const int i = 0;

'i' a une liaison interne, et ne peut donc pas être appelé à partir de l'extérieur de cette unité de traduction. Cependant, à nouveau, sauf si vous utilisez son adresse, il sera plus susceptible d'être traité comme un type-safe 0.

Une chose est intéressant de souligner, c'est que la déclaration suivante:

const int i1 = 0;

est exactement le même que static const int i = 0. Une variable dans un espace de noms déclarés avec const et pas explicitement déclarée en extern est implicitement statique. Si vous pensez à ce sujet, il était de l'intention du comité C++ pour permettre l' const variables déclarées dans l'en-tête des fichiers sans avoir toujours besoin de l' static mot-clé pour éviter la rupture de l'ODR.

Portée De Classe

class A {
public:
  static const int i = 0;
};

Dans l'exemple ci-dessus, la norme spécifie explicitement que"i' n'a pas besoin d'être défini si son adresse n'est pas nécessaire. En d'autres termes, si vous utilisez uniquement 'i' en tant que type-safe 0 alors le compilateur ne la définit pas. Une différence entre la classe et l'espace de versions, c'est que l'adresse de 'i"(si utilisé dans deux ou plusieurs unités de traduction) sera la même pour le membre de la classe. Lorsque l'adresse est utilisée, vous devez disposer d'une définition:

// a.h
class A {
public:
  static const int i = 0;
};

// a.cc
#include "a.h"
const int A::i;            // Definition so that we can take the address

28voto

Ferruccio Points 51508

C'est une petite optimisation de l'espace.

Quand vous dites

const int foo = 42;

Vous n'êtes pas à la définition d'une constante, mais la création d'un accès en lecture seule variable. Le compilateur est assez intelligent pour utiliser 42 quand il voit le foo, mais il permettra également d'allouer de l'espace dans la initialisée zone de données. Ceci est fait parce que, tel que défini, toto a une liaison externe. Une autre unité de compilation peut dire:

extern const int foo;

Pour obtenir l'accès à sa valeur. Ce n'est pas une bonne pratique, car cette unité de compilation n'a aucune idée de la valeur de toto. Il sait juste que c'est un const int et a pour recharger la valeur de la mémoire quand il est utilisé.

Maintenant, en déclarant qu'il est statique:

static const int foo = 42;

Le compilateur ne peut faire son habitude, l'optimisation, mais il peut aussi dire "hey, personne en dehors de cette unité de compilation peut voir foo et je sais qu'il est toujours 42 donc il n'est pas nécessaire d'allouer de l'espace pour cela."

9voto

Kevin Points 7334

Il manque un 'int'. Il devrait être:

const static int foo = 42;

En C et C++, il déclare une constante entière avec le fichier local de la portée de la valeur 42.

Pourquoi 42? Si vous ne connaissez pas déjà (et il est difficile de croire que vous n'avez pas), c'est une refernce de la Réponse à la Vie, l'Univers et Tout.

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