Dichiarazione di variabili all’interno di un’istruzione switch

Ho visto alcune risposte a questo problema e ho capito: non è ansible dichiarare e assegnare variabili all’interno di uno switch . Ma mi chiedo se il seguente è corretto a lanciare un errore dicendo

errore: espressione attesa prima di ‘int’

Codice:

 switch (i) { case 0: int j = 1; break; } 

Perché mettere una chiamata a NSLog() prima che si verifichi nessun errore?

 switch (i) { case 0: NSLog(@"wtf"); int j = 1; break; } 

In realtà puoi dichiarare variabili all’interno di un interruttore se lo fai secondo la syntax della lingua. Stai ricevendo un errore perché ” case 0: ” è un’etichetta e in C è illegale avere una dichiarazione come prima istruzione dopo un’etichetta – nota che il compilatore si aspetta un’espressione , come una chiamata al metodo, un’assegnazione normale, ecc. (Per quanto possa essere bizzarro, questa è la regola).

Quando inserisci NSLog () per primo, hai evitato questa limitazione. È ansible racchiudere il contenuto di un caso in {} parentesi graffe per introdurre un blocco dell’ambito o spostare la dichiarazione della variabile all’esterno dello switch. Quello che scegli è una questione di preferenze personali. Tieni presente che una variabile dichiarata in {} parentesi è valida solo all’interno di tale ambito, quindi qualsiasi altro codice che lo utilizza deve apparire anche all’interno di tali parentesi.


Modificare:

A proposito, questa stranezza non è così rara come si potrebbe pensare. In C e Java, è anche illegale usare una dichiarazione di variabile locale come istruzione solitaria (che significa “non circondata da parentesi graffe) in un for , while , o do loop, o anche in clausole if e else . (In realtà, questo è coperto nel puzzle n. 55 di “Java Puzzlers” , che consiglio vivamente.) Penso che generalmente non scriviamo errori di questo tipo, perché ha poco senso dichiarare una variabile come unica affermazione in tali contesti. costrutti case , tuttavia, alcune persone omettono le parentesi poiché l’istruzione break è l’istruzione critica per il controllo del stream.

Per vedere il compilatore che si adatta, copia questo snippet orribile e inutile nel tuo codice (Objective-) C:

 if (1) int i; else int i; for (int answer = 1; answer <= 42; answer ++) int i; while (1) int i; do int i; while (1); 

Ancora un altro motivo per usare sempre {} parentesi per delimitare il corpo di tali costrutti. 🙂

Mi sono imbattuto in questo problema in precedenza e la conclusione è stata che hai inserito il codice all’interno di un blocco.

 switch (i) { case 0: { int j = 1; break; } } 

Un’altra soluzione semplice che utilizzo è quella di aggiungere un’espressione vuota (punto e virgola) prima della dichiarazione. Questo evita di limitare l’ambito della variabile a un blocco di codice (o con alcune istruzioni caso con blocchi di codice e alcuni senza).

 switch (i) { case 0:; int j = 1; break; }