View Full Version : [c] differenza di assegnamento letterale tra array e puntatori
Mi potete spiegare perché se definisco una stringa come array di carattere inizializzato così:
char a[] ="ciao";
posso modificare le sue lettere con
a[2]= 'x';
mentre non posso farlo se utilizzo un puntatore così:
char * a ="ciao";
Credo che sia una cosa piuttosto semplice sulla quale però vorrei fare chiarezza.
grazie
Alex_87_xelA
16-12-2008, 21:01
Mi potete spiegare perché se definisco una stringa come array di carattere inizializzato così:
char a[] ="ciao";
posso modificare le sue lettere con
a[2]= 'x';
mentre non posso farlo se utilizzo un puntatore così:
char * a ="ciao";
Credo che sia una cosa piuttosto semplice sulla quale però vorrei fare chiarezza.
grazie
con il primo è creato un vettore di caratteri dalla dimensione finita (nel tuo caso = 4 + il terminatore \0)
quindi con l'assegnazione inizziale si copiano nelle celle del vettore i vari caratteri
char a[] ="ciao"; <--- questo è uguale a questo ---> char a[] ={'c', 'i', 'a', 'o'};
e quindi il compilatore in modo automatico "contando" il numero di caratteri da inserire + il terminatore fa questo :
char a[5] = "ciao\0";
che poi effettivamente sarebbe questo
a[0] = 'c';
a[1] = 'i'';
a[2] = 'a';
a[3] = 'o';
a[4] = '\0';
quindi ovviamente un vettore con dei dati può essere modificato e qui non penso ci dovrebbero essere molti problemi in questo primo caso o no ?
per il secondo abbiamo :
char * a ="ciao";
cioè un puntatore di caratteri che punta ad una stringa costante ... perchè di "default" la stringa tra apici è costante.
quindi tramite puntatore vuoi modificare una stringa costante e questo porta all'errore.
spero di essere stato chiaro.
ciao
DanieleC88
16-12-2008, 22:16
Dipende da dove viene inserita quella stringa. Ad ogni modo, l'array viene posizionata sullo stack, se è dichiarata internamente ad una funzione, mentre nel secondo caso si ha un puntatore sullo stack che punta a dati in una sezione a sola lettura nel file. ;)
stefano_ba
17-12-2008, 11:21
mentre non posso farlo se utilizzo un puntatore così:
char * a ="ciao";
a e' un puntatore a char quindi punta alla prima locazione dell'array.
Con l'assegnazione ="ciao" cerchi di scrivere una stringa nello spazio di un char e per questo il compilatore ti da' errore.
Per scrivere l'intera stringa DEVI necessariamente farlo carattere per carattere, assegni la prima lettera, incrementi il puntatore al carattere successivo e cosi' via; ossia un qualcosa del genere:
char *a="c";
a++;
char *a="i";
a++;
char *a="a";
a++;
.....
Viceversa nella libreria standard che si occupa delle stringe esistono delle funzioni che operano la copiatura di una stringa su di un altra. Dai un occhiata alle strcpy() strncpy() (STRing CopY) ed altre funzioni presenti in string.h
P.S: nella scrittura ricordati di gestire correttamente il carattere di fine stringa \0 altrimenti se non inserisci un terminatore otterrai dei risultati inattesi nel momento in cui andrai a rileggere quello stesso vettore. Le funzioni che ti ho segnalato gestiscono anche questo aspetto.
ringrazio tutti delle risposte.. le prime due mi semnbrano assai coerenti mentre non mi sembra quella di stefano. forse non a capito la mia richiesta.
stefano_ba
18-12-2008, 08:25
Nella mia risposta ho presupposto che tu abbia gia' allocato la memoria utilizzando o la classica char a[] = "cane"; oppure usando una calloc()/malloc()
Dai un occhiata alla pagina http://www.xelon.it/appunti/programmazione/stringhe.php in cui tratta l'utilizzo delle stringhe.
Con un puntatore puoi modificare il singolo elemento puntato dal puntatore stesso, dipende dal tipo di puntatore che stai utilizzando se di tipo char-int-... o quant'altro, indipendentemente dove questo punti.
Gli array sono allocati nello stack non su di un file; DanieleC88 a quale file ti riferisci?
Risposta di Alex_87_xelA: la stringa non e' definita come costante, e' solo stato assegnato un contenuto ben definito alle locazioni di memoria che la contiene. Forse ti stai confondendo con la parola chiave Constant che e' solo una indicazione nella fase di compilazione del programma.
In C utilizzando i puntatori posso andare a modificare qualsiasi locazione di memoria sia sullo stack che nella zona delle istruzioni del programma stesso, e' compito del sistema operativo evitare che un programma possa arrecare danni al sistema operativo stesso.
DanieleC88
18-12-2008, 10:27
Gli array sono allocati nello stack non su di un file; DanieleC88 a quale file ti riferisci?
Infatti io mi riferivo alla stringa, non all'array (rileggi, ho detto proprio quello: array sullo stack, stringhe costanti in memoria). Se compili, ad esempio, con GCC e cerchi dov'è definita la tua stringa costante, vedrai che il puntatore sarà inizializzato ad un valore che è preservato nella sezione .rodata dell'eseguibile (basta caricarlo in un segmento di memoria a sola lettura e i tuoi tentativi di scrittura causeranno un segmentation fault).
vBulletin® v3.6.4, Copyright ©2000-2025, Jelsoft Enterprises Ltd.