2010-10-01 37 views
6

Sono nuovo nella programmazione in C, quindi sto provando molte cose diverse per provare a familiarizzare con la lingua.inizializzazione di una variabile statica nell'intestazione

ho scritto il seguente:

File q7a.h:

static int err_code = 3; 
void printErrCode(void); 

File q7a.c:

#include <stdio.h> 
#include "q7a.h" 

void printErrCode(void) 
{ 
     printf ("%d\n", err_code); 
} 

File q7main.c:

#include "q7a.h" 

int main(void) 
{ 
     err_code = 5; 
     printErrCode(); 

     return 0; 
} 

ho poi corse il seguente nel makefile (sto usando un sistema operativo Linux)

gcc –Wall –c q7a.c –o q7a.o 
gcc –Wall –c q7main.c –o q7main.o 
gcc q7main.o q7a.o –o q7 

l'uscita è 3.

Perché succede questo ?

Se si inizializza una variabile statica (in pratica qualsiasi variabile) nel file di intestazione, quindi se 2 file includono lo stesso file di intestazione (in questo caso q7.c e q7main.c) il linker intende fornire un errore per aver definito il doppio var?

E perché il valore 5 non è inserito nella variabile statica (dopotutto è statico e globale)?

Grazie per l'aiuto.

+2

Solo una nota: mai, in nessuna circostanza, TUTTAVIA, inizializzare le variabili in un file di intestazione. È una pratica assolutamente scorretta. Capisco che lo stai facendo ora come esercizio di apprendimento. –

+1

@ user82238, a meno che non sia un const statico, allora forse. –

risposta

23

static significa che la variabile viene utilizzata solo all'interno dell'unità di compilazione e non sarà esposta al linker, quindi se si dispone di un static int in un file di intestazione e lo si include da due file .c separati, si avranno due discreti copie di quell'int, che molto probabilmente non è affatto quello che vuoi.

Invece, è possibile considerare extern int e scegliere un file .c che lo definisce effettivamente (ovvero solo int err_code=3).

+1

Non intendi * define * invece di * dichiarare * nella tua ultima frase? – schot

+0

Sì. Corretto. – EboMike

0

Le variabili statiche donot hanno un collegamento esterno che significa che non è possibile accedervi al di fuori dell'unità di traduzione in cui vengono definiti. Quindi nel tuo caso quando q7.h è # include'ed in entrambe le unità di traduzione q7a.c e q7main.c ... esistono due copie diverse nei loro file .o corrispondenti. Questo è il motivo per cui il linker non segnala un errore perché entrambe le copie non sono viste dal linker mentre si esegue il collegamento di simboli esterni.

0

Durante la ricerca di piccole dimensioni è venuto a sapere che possiamo dichiarare variabile nel file di intestazione, ma in uno dei file di origine include che dovrebbe avere definizione per tale variabile.

Invece se definiamo una variabile nel file di intestazione. nei file di origine in cui è incluso questo file di intestazione, verranno create definizioni che causano più definizioni.

Una variabile statica dovrebbe essere dichiarata con nel file in cui lo usiamo non dovrebbe essere esposto al file di intestazione.

Spero di dare le giuste informazioni. Se sbaglio, sentiti libero di correggere le mie affermazioni nei tuoi commenti.

Problemi correlati