Classes de stockage en C

| Classe | Mot-clé | Portée | Emplacement mémoire | Durée de vie | Valeur initiale |
|---|---|---|---|---|---|
| Automatique | auto | Bloc local | Pile (stack) | Durée du bloc | Indéfinie (garbage) |
| Externe | extern | Tout le programme (multi-fichiers) | Segment de données | Durée du programme | 0 / NULL |
| Statique | static | Bloc local ou fichier | Segment de données | Durée du programme | 0 (une seule fois) |
| Registre | register | Bloc local | Registre CPU (si disponible) | Durée du bloc | Indéfinie (garbage) |
1. Classe automatique — auto
auto est la classe par défaut de toute variable déclarée dans un bloc ou une fonction. Le mot-clé auto est optionnel (presque jamais écrit explicitement). La variable est créée à l'entrée du bloc et détruite à sa sortie.auto int age; /* explicite — rarement écrit */
int age; /* équivalent — classe auto implicite */Exemple n°1 — Portée de blocs imbriqués avec auto
#include <stdio.h>
int main(void)
{
auto int j = 1; /* bloc 1 */
{
auto int j = 2; /* bloc 2 — nouvelle variable j, masque le j du bloc 1 */
{
auto int j = 3; /* bloc 3 — nouvelle variable j, masque les deux précédentes */
printf("bloc 3 — j = %d\n", j);
} /* j de bloc 3 détruite ici */
printf("bloc 2 — j = %d\n", j);
} /* j de bloc 2 détruite ici */
printf("bloc 1 — j = %d\n", j);
return 0;
} /* j de bloc 1 détruite ici */bloc 3 — j = 3 bloc 2 — j = 2 bloc 1 — j = 1
Chaque bloc possède sa propre variable j indépendante. À la sortie d'un bloc, la variable locale est détruite et la variable du bloc parent redevient visible.
auto n'est jamais écrit en C moderne — toute variable locale est automatique par défaut. En C++11, auto a été réutilisé pour la déduction de type, ce qui est une signification complètement différente.2. Classe externe — extern
extern déclare qu'une variable ou une fonction est définie dans un autre fichier. Il permet de partager des données globales entre plusieurs fichiers source d'un même projet sans redéfinir la variable./* Fichier A — définition (une seule fois dans tout le projet) */
int compteur = 3;
/* Fichier B — déclaration (autant de fichiers que nécessaire) */
extern int compteur; /* pas d'initialisation — la variable existe déjà dans A */Exemple n°2 — Variable partagée entre deux fichiers
/* ───── main.c ───── */
#include <stdio.h>
int compteur; /* définition — mémoire allouée ici */
extern void methode_globale(void);
int main(void)
{
compteur = 3;
methode_globale();
return 0;
}/* ───── utilitaire.c ───── */
#include <stdio.h>
extern int compteur; /* déclaration — pas de nouvelle allocation */
void methode_globale(void)
{
printf("compteur est : %d\n", compteur);
}gcc main.c utilitaire.c -o main
./maincompteur est : 3
extern est une déclaration (annonce qu'une variable existe ailleurs) — pas une définition (pas d'allocation mémoire). Il ne faut jamais initialiser une variable extern:extern int x = 5; /* incorrect — extern + initialisation = redéfinition */
extern int x; /* correct — simple déclaration */3. Classe statique — static
static a deux effets selon le contexte. Appliqué à une variable locale, il prolonge sa durée de vie à toute l'exécution du programme tout en conservant sa portée locale — la variable persiste entre les appels. Appliqué à une variable ou fonction globale, il restreint sa visibilité au fichier source courant.static int compteur = 10; /* variable statique — initialisée une seule fois */Exemple n°3 — Variable locale statique qui persiste entre les appels
#include <stdio.h>
void func(void);
static int compteur = 3; /* globale statique — visible dans ce fichier uniquement */
int main(void)
{
while (compteur--) {
func();
}
return 0;
}
void func(void)
{
static int i = 5; /* initialisée à 5 une seule fois — conserve sa valeur */
i++;
printf("i = %d | compteur = %d\n", i, compteur);
}i = 6 | compteur = 2 i = 7 | compteur = 1 i = 8 | compteur = 0
La variable locale i conserve sa valeur (6, puis 7, puis 8) d'un appel à l'autre. Sans static, elle serait réinitialisée à 5 à chaque appel.
Exemple n°4 — Compteur d'appels avec variable statique
#include <stdio.h>
void compter_appels(void)
{
static int nb = 0; /* initialisée à 0 une seule fois */
nb++;
printf("Appel n°%d\n", nb);
}
int main(void)
{
compter_appels();
compter_appels();
compter_appels();
return 0;
}Appel n°1 Appel n°2 Appel n°3
Contexte de static | Effet sur la portée | Effet sur la durée de vie |
|---|---|---|
| Variable locale | Inchangée (bloc local) | Prolongée à toute l'exécution |
| Variable globale | Restreinte au fichier courant | Toute l'exécution (déjà le cas) |
| Fonction | Restreinte au fichier courant | — |
4. Classe registre — register
register est un indice au compilateur pour stocker la variable dans un registre du processeur (plutôt que dans la RAM), ce qui accélère l'accès. C'est une suggestion — le compilateur peut l'ignorer si aucun registre n'est disponible.register int compteur; /* suggestion : stocker dans un registre CPU */Exemple n°5 — Usage typique : compteur de boucle
#include <stdio.h>
int main(void)
{
register int i;
long somme = 0;
for (i = 0; i < 1000000; i++) {
somme += i;
}
printf("Somme = %ld\n", somme);
return 0;
}register n'a pas d'emplacement en RAM — il est donc impossible d'obtenir son adresse avec l'opérateur &:register int poids;
int *ptr = &poids; /* ERREUR — address of register variable requested */register est déprécié. Les compilateurs modernes (GCC, Clang) optimisent l'usage des registres bien mieux que le programmeur ne peut le faire manuellement. En pratique, register n'est plus utilisé dans le code moderne.Récapitulatif
| Critère | auto | extern | static | register |
|---|---|---|---|---|
| Portée | Bloc local | Multi-fichiers | Bloc local ou fichier | Bloc local |
| Emplacement | Pile | Segment de données | Segment de données | Registre CPU |
| Durée de vie | Durée du bloc | Durée du programme | Durée du programme | Durée du bloc |
| Valeur initiale | Garbage | 0 / NULL | 0 (une seule fois) | Garbage |
| Opérateur & | Permis | Permis | Permis | Non permis |
| Usage typique | Variables locales (défaut) | Partage multi-fichiers | Persistance entre appels | Compteurs (obsolète) |
Discussion (0)
Soyez le premier à laisser un commentaire !
Laisser un commentaire
Votre commentaire sera visible après modération.