PDA

View Full Version : [C++] Notazioni fuori di testa


biowep
22-10-2014, 15:53
Salve, sto studiando il C++ e mi sono imbattuto in una discussione si stackoverflow dove viene spiegata la differenza tra mettere la keyword const in una posizione piuttosto che in un'altra.
http://stackoverflow.com/questions/1143262/what-is-the-difference-between-const-int-const-int-const-int-const?answertab=active#tab-top

Quello che non capisco è il caso in cui invece di una singola dichiarazione faccio una dichiarazione di variabili multipla.

int main() {
int v = 12345;
int * const p1 = &v;
int * const * const a = &p1, b = v;
cout << **a << ", " << b << "\n";//output: "12345, 12345"
}
Nell'esempio a è una roba assurda mentre b è un semplice int. Strano, molto strano, ma posso capire.
Ora facciamo un altro esempio
int main() {
const int * c = &v, d = v;
cout << *c << ", " << d << "\n";
//d = 50;//error: assignment of read-only variable 'd'
}
In questo caso c è un puntatore ad un intero costante mentre d è un intero costante, WHAT????

Perché se metto "const" prima dovrebbe far parte del tipo mentre se lo metto dopo non fa parte del tipo? Che mente malata bisogna avere per inventare una sintassi tanto difficile, piena di particolarità e casi speciali?
Quale è il criterio, nel caso di dichiarazione di più variabili? Intendo: come posso sapere a priori cosa fa parte del tipo e cosa no, senza fare dei test, solo leggendo il codice.

tomminno
22-10-2014, 16:19
Premesso che un doppio puntatore const non serve a niente, quando insegnarono a me il C dissero che le dichiarazioni si leggevano al contrario :D

int * const * const=const pointer to const pointer to int
int * const = const pointer to int
const int * = pointer to const int

Messa così non è troppo difficile da capire ;)

biowep
22-10-2014, 16:31
Ok, ma quale parte del nome si tiene quando si dichiarano più variabili nella stessa istruzione? Perché la costante messa prima ha più valore di quella messa dopo?

vendettaaaaa
22-10-2014, 19:44
Divertente:
http://i59.tinypic.com/2vsnhps.png

biowep
22-10-2014, 21:16
Provando e riprovando mi sembra di capire che il tipo che condividono le varie variabili sia fin dove inizia il nome del tipo :D
Ma c'è un'eccezzione, const int ed int cost sono la stessa cosa (nel senso che entrambe le variabili saranno interi costanti in entrambi i casi)
Me lo potete confermare?

@vendettaaaaa
Scusami, il valore è 12345, ho sbagliato a riportare purtroppo. Ho corretto anche il primo post.

AnonimoVeneziano
23-10-2014, 00:14
Nella dichiarazioni dei puntatori a variabili quando lo fai multiple volte su una riga devi ripetere il puntatore, tipo:

int *a, c;

a e' int*
c e' int

int *a, *c;

a e c sono int*

int a, *const b;

a e' int
b e' int * const (puntatore costante a un int)

Ciao

vendettaaaaa
23-10-2014, 18:31
Provando e riprovando mi sembra di capire che il tipo che condividono le varie variabili sia fin dove inizia il nome del tipo :D
Ma c'è un'eccezzione, const int ed int cost sono la stessa cosa (nel senso che entrambe le variabili saranno interi costanti in entrambi i casi)
Me lo potete confermare?

@vendettaaaaa
Scusami, il valore è 12345, ho sbagliato a riportare purtroppo. Ho corretto anche il primo post.
Intendevo un'altra cosa!
"Codice PHP: " e dentro c'è codice C++ :D

SnakePlissken
25-10-2014, 09:21
...quando insegnarono a me il C dissero che le dichiarazioni si leggevano al contrario :D

int * const * const=const pointer to const pointer to int
int * const = const pointer to int
const int * = pointer to const int

Messa così non è troppo difficile da capire ;)

C'è anche un altro modo di vederla, più pratico: il const si riferisce a tutto quello che c'è a destra (e il tipo è tutto quello che c'è a sinistra):
int * const * const p;
è const (int**)p: int * [const] * [const] | p
è const (int*)*p: int * [const] | * [const] p

int * const q;
è const (int*)q: int * [const] | q

const int * r;
è const (int)*r: [const] | [int] * r

int const ** s;
è const (int)**s: int [const] | ** s

int * const ** const * const z;
è const (int****)z: int * [const] ** [const] * [const] | z
è const (int***)*z: int * [const] ** [const] | * [const] z
è const (int*)***z: int * [const] | ** [const] * [const] z


In pratica, riprendendo l'ultimo esempio:
z = a; // Errore
*z = b; // Errore
**z = c; // OK
***z = d; // Errore
****z = e; // OK

biowep
25-10-2014, 11:06
//

Ma la sintassi con le parentesi non compile.
Ad es: const (int**)p;//error: expected primary-expression before 'const'
@vendettaaaaa
L'ho usato solo per il colore della sintassi.