syntax - C'è un'istruzione goto in Java?




keyword (21)

Sono confuso su questo. Alla maggior parte di noi è stato detto che non c'è alcuna istruzione goto in Java.

Ma ho scoperto che è una delle parole chiave in Java. Dove può essere utilizzato? Se non può essere usato, perché è stato incluso in Java come parola chiave?


Answers

La parola chiave esiste, ma non è implementata.

L'unica buona ragione per usare goto a cui riesco a pensare è questa:

for (int i = 0; i < MAX_I; i++) {
    for (int j = 0; j < MAX_J; j++) {
        // do stuff
        goto outsideloops; // to break out of both loops
    }
}
outsideloops:

In Java puoi fare questo in questo modo:

loops:
for (int i = 0; i < MAX_I; i++) {
    for (int j = 0; j < MAX_J; j++) {
        // do stuff
        break loops;
    }
}

Per vietare dichiarazioni di variabili con lo stesso nome.

ad es. int i = 0, goto;


No, goto non è usato in Java, nonostante sia una parola riservata. Lo stesso è vero per const . Entrambi questi sono usati in C ++, che è probabilmente la ragione per cui sono riservati; l'intenzione era probabilmente quella di evitare di confondere i programmatori C ++ in migrazione verso Java, e forse anche di mantenere l'opzione di usarli nelle revisioni successive di Java.



Ovviamente è una parola chiave, ma non è usata a livello di codice sorgente.

Ma se usi jasmin o un altro linguaggio di livello inferiore, che viene trasformato in bytecode, allora "goto" è lì


L' elenco di parole chiave Java specifica la parola chiave goto , ma è contrassegnato come "non usato".

Era nella JVM originale (vedi risposta di @VitaliiFedorenko ), ma poi rimosso. Probabilmente è stato mantenuto come parola chiave riservata nel caso in cui dovesse essere aggiunto a una versione successiva di Java.

Se goto non era presente nell'elenco e successivamente viene aggiunto alla lingua, il codice esistente che utilizzava la parola goto come identificatore (nome variabile, nome metodo, ecc.) Si interrompeva. Ma poiché goto è una parola chiave, tale codice non verrà nemmeno compilato nel presente, e rimane possibile farlo effettivamente fare qualcosa in seguito, senza rompere il codice esistente.


Un esempio di come utilizzare le etichette "continue" in Java è:

public class Label {
    public static void main(String[] args) {
        int temp = 0;
        out: // label
        for (int i = 0; i < 3; ++i) {
            System.out.println("I am here");
            for (int j = 0; j < 20; ++j) {
                if(temp==0) {
                    System.out.println("j: " + j);
                    if (j == 1) {
                        temp = j;
                        continue out; // goto label "out"
                    }
                }
            }
        }
        System.out.println("temp = " + temp);
    }
}

risultati:

I am here // i=0
j: 0
j: 1
I am here // i=1
I am here // i=2
temp = 1

Nota che puoi sostituire la maggior parte degli usi benevoli di goto di

  • ritorno

  • rompere

  • etichetta di rottura

  • buttati dentro try-catch-finally



Come è stato sottolineato, non c'è goto in Java, ma la parola chiave è stata riservata nel caso in cui a Sun piacesse aggiungere goto a Java un giorno. Volevano essere in grado di aggiungerlo senza rompere troppo codice, quindi hanno riservato la parola chiave. Si noti che con Java 5 hanno aggiunto la parola chiave enum e non ha infranto neanche quel tanto codice.

Sebbene Java non abbia goto , ha alcuni costrutti che corrispondono ad alcuni usi di goto , ovvero la possibilità di break e continue con loop nominati. Inoltre, finally può essere pensato come una sorta di goto contorto.


Perché non è supportato e perché vorresti una parola chiave goto che non facesse nulla o una variabile chiamata goto ?

Sebbene tu possa usare l' break label; e continue label; dichiarazioni per fare efficacemente ciò che fa goto . Ma non lo raccomanderei.

public static void main(String [] args) {

     boolean t = true;

     first: {
        second: {
           third: {
               System.out.println("Before the break");

               if (t) {
                  break second;
               }

               System.out.println("Not executed");
           }

           System.out.println("Not executed - end of second block");
        }

        System.out.println("End of third block");
     }
}

Java ha GOTO a livello di bytecode come goto e goto_w . Tuttavia, nel linguaggio Java non c'è GOTO.

Sebbene Java proibisca GOTO, Microsoft ha deciso di mantenerlo nell'arsenale .NET. C # consente il GOTO:

goto (Riferimento C #)

L'istruzione goto trasferisce il controllo del programma direttamente su un'istruzione etichettata. Un uso comune di goto è il trasferimento del controllo a un'etichetta switch-case specifica o l'etichetta predefinita in un'istruzione switch. L'istruzione goto è anche utile per uscire da loop profondamente annidati.

Dato che C # (principale concorrente di Java in .NET) consente GOTO, non vedo perché sarebbe un grosso problema se lo avesse anche Java.

Esistono soluzioni alternative come questo progetto:

JavaGoto

È utile quando si converte il codice legacy. Ad esempio, un codice Fortran precedente è così complicato che mantenere intatti i GOTO può essere la soluzione più efficiente prima di migrare il codice ai costrutti corretti.

L'indennità di Goto in C # non ha provocato l'abuso di GOTO, e dubito che Java sarebbe peggio se lo avessero permesso.



Neanche io sono un fan del goto , perché di solito rende il codice meno leggibile. Comunque credo che ci siano delle eccezioni a questa regola (specialmente quando si tratta di lesseri e parser!)

Naturalmente puoi sempre portare il tuo programma in Kleene Normalform traducendolo in qualcosa di simile ad assembler e poi scrivere qualcosa del genere

int line = 1;
boolean running = true;
while(running)
{
    switch(line++)
    {
        case 1: /* line 1 */
                break;
        case 2: /* line 2 */
                break;
        ...
        case 42: line = 1337; // goto 1337
                break;
        ...
        default: running = false;
                break;
    }
}

(Quindi in pratica scrivi una VM che esegue il tuo codice binario ... dove la line corrisponde al puntatore dell'istruzione)

Questo è molto più leggibile del codice che usa goto , non è vero?


È molto considerato una di quelle cose che non si fanno, ma probabilmente è stato elencato come una parola riservata per evitare confusione per gli sviluppatori.


Sono riservati per uso futuro (vedi: Parole chiave di linguaggio Java )

Le parole chiave const e goto sono riservate, anche se non sono attualmente utilizzate.

Il motivo per cui non esiste alcuna istruzione goto in Java può essere trovato in " The Java Language Environment ":

Java non ha alcuna istruzione goto. Gli studi hanno dimostrato che goto è (errato) usato più spesso che semplicemente "perché è lì". Eliminare goto ha portato ad una semplificazione del linguaggio - per esempio, non ci sono regole sugli effetti di un goto nel mezzo di un'istruzione for. Gli studi condotti su circa 100.000 righe di codice C hanno determinato che circa il 90 percento delle dichiarazioni goto erano utilizzate esclusivamente per ottenere l'effetto di scoppiare di cicli annidati. Come accennato in precedenza, interruzione multi-livello e continua rimuovere la maggior parte della necessità di istruzioni goto.


Perché sebbene il linguaggio Java non lo usi, il bytecode di JVM lo fa.


No, per fortuna, non c'è goto in Java.

La parola chiave goto è solo riservata, ma non utilizzata (lo stesso vale per const ).


È importante capire che il goto construct è il resto dei giorni in cui i programmatori programmavano in codice macchina e linguaggio assembly. Poiché tali lingue sono così basilari (come in ogni istruzione fa solo una cosa), il flusso di controllo del programma viene eseguito completamente con le istruzioni goto (ma nel linguaggio assembly, queste sono chiamate istruzioni jump o branch ).

Ora, sebbene il linguaggio C sia piuttosto di basso livello, può essere pensato come linguaggio di assemblaggio di alto livello - ogni istruzione e funzione in C può essere facilmente suddivisa in istruzioni di linguaggio assembly. Sebbene C non sia il linguaggio principale per programmare i computer al giorno d'oggi, è ancora molto usato nelle applicazioni di basso livello, come i sistemi embedded. Poiché la funzione di C rispecchia in modo così stretto la funzione del linguaggio di assemblaggio, ha senso solo che goto sia incluso in C.

È chiaro che Java è un'evoluzione di C / C ++. Java condivide molte caratteristiche di C, ma riassume molti più dettagli, e quindi è semplicemente scritto in modo diverso. Java è un linguaggio di alto livello, quindi non è necessario avere caratteristiche di basso livello come goto quando più costrutti di alto livello come le funzioni, per, per ogni ciclo e mentre il flusso di controllo del programma. Immagina se fossi in una funzione e facessi un goto su un'etichetta in un'altra funzione. Cosa succederebbe quando l'altra funzione ritornasse? Questa idea è assurda.

Questo non significa necessariamente che Java includa la dichiarazione goto ma non lo lascerà compilare, ma è importante sapere perché goto è mai stato utilizzato in primo luogo, nelle applicazioni di livello inferiore, e perché non ha senso da utilizzare in Java.


Per evitare che le persone vengano uccise dai velociraptor.


Java passa i riferimenti agli oggetti in base al valore.





java syntax keyword goto