miniaturadeimagen|Tecla "GOTO" en la computadora doméstica ZX Spectrum de 1982, implementada con BASIC nativo (entrada de comando con una sola tecla). GOTO (también goto, go to, GO TO, GoTo y similares; del inglés go to, «ir hasta», «ir hacia», «ir a») es una instrucción que existe en diversos lenguajes de programación.

La instrucción transfiere el control a un punto determinado del código donde debe continuar la ejecución. El punto al que se salta, viene indicado por una etiqueta. GOTO es una instrucción de salto incondicional.

La instrucción GOTO ha sido menospreciada en los lenguajes de alto nivel, debido a la dificultad que presenta para poder seguir adecuadamente el flujo del programa.

En la actualidad, la funcionalidad de la instrucción sigue existiendo en todos los lenguajes de programación bajo nombres específicos y con un campo de uso delimitado. Por lo general se restringe su uso a una estructura específica. Lo más habitual es encontrarla como una instrucción de salida de una estructura de control (en bucles FOR...NEXT como Exit FOR, en bucles DO...LOOP como Exit DO, etc.). Y el punto al que se salta, no es arbitrario sino que se salta a puntos específicos coherentes con un flujo fácil de seguir, por lo general el salto es a la instrucción siguiente a la del final de la estructura. Es decir GOTO se ha transformado (bajo la apariencia de otra palabra reservada) como un salto incondicional, pero a un punto concreto con relación a la estructura a la que da soporte.

Historia El salto incondicional no es necesario en un lenguaje de programación de alto nivel. Ya en los años 60 se dieron cuenta de ello, desarrollándose técnicas de programación que no la utilizaban (ver programación estructurada).

Los compiladores e intérpretes de lenguajes de programación aún la tienen, como recurso de programación, pero las técnicas de programación, como la programación estructurada, desaconsejan o prohíben su uso.

El salto incondicional es una instrucción de programación por la cual el contador de programa toma un valor nuevo, que el programador indica. Este método se empleó en las primeras técnicas de programación y en lenguaje de máquina. Cuando la ejecución del programa llega a la instrucción GOTO, la siguiente sentencia ejecutada será la que se encuentre en :Etiqueta.

El abuso de esta, aparentemente ágil, sentencia da lugar a lo que se suele denominar como código espagueti, porque ese es el aspecto del seguimiento del programa, un plato de "espagueti"; esta es una descalificación de una aplicación informática, equivalente a "chapuza indescifrable".

Variaciones Se pueden encontrar variaciones de la instrucción GOTO. En BASIC, la instrucción ON GOTO puede seleccionar de una lista de diferentes puntos de un programa a los que saltar. Podría ser interpretado como un antecesor de la instrucción switch/case. También, en FORTRAN y algunas versiones de BASIC la línea a la que saltar podía ser indicada mediante una expresión aritmética. Esto último era evitado ya que el código se hacía aún más ilegible teniendo en cuenta la necesidad de hacer los cálculos de la expresión de control para saber el destino del flujo del programa.

Controversia sobre el uso de GOTO A diferencia de la llamada a una función, no se requiere ningún tipo de preparación o estructura de código para utilizar un GOTO. Como resultado, es más sencillo obtener código inconsistente, incompleto o complicado de mantener. Justamente por ello en los años 60 y 70, cuando surgió la programación estructurada, la comunidad informática se expresó a favor de otras instrucciones de control (if o bucles for y do/while) en lugar de GOTO.

Tal creencia está tan arraigada que el GOTO es muy criticado por los dedicados a la enseñanza de la programación, que lo suelen desaconsejar. Por el otro lado, algunos que si bien admiten el uso de un GOTO como una práctica desaconsejable* Peter Bishop: Programación avanzada en BASIC, Ediciones Anaya Multimedia año-1990 ISBN 978-84-7614-013-0 (página 86): reconocen que este es la mejor opción para algunas pocas tareas puntuales* Peter Bishop: Programación avanzada en BASIC, Ediciones Anaya Multimedia año-1990 ISBN 978-84-7614-013-0 (página 86): en algunos lenguajes de programación (manejo de excepciones por ejemplo). Además, por lo general se programan macros o equivalentes para evitar la utilización de GOTO.

Una crítica famosa a la instrucción en cuestión es una carta redactada por Edsger Dijkstra llamada "Go To Statement Considered Harmful" (Instrucción Go To Considerada Dañina'). En ella Dijkstra argumenta que el uso irrestricto de GOTO debería ser prohibido en lenguajes de alto nivel ya que dificultan el análisis y la verificación de la corrección de los programas (especialmente aquellos que contienen ciclos). Por el otro lado, Donald Knuth en su libro "Structured Programming with goto Statements" (Programación estructurada con instrucciones Goto), tiene en cuenta ciertas situaciones en las que se utilizaría GOTO. Por lo general, se trata de situaciones en las que una estructura de programación en particular no está disponible y GOTO puede simularla eficientemente.

Interacción de GOTO dentro de otras estructuras de control La sentencia GOTO, no solo puede aparecer a lo largo del listado de instrucciones de un programa, sino que incluso puede enviar el flujo dentro de una estructura de control o fuera de la misma.

Es patente, la complejidad de entender un código cuyas estructuras de control lo estuvieran también cruzadas por sentencias GOTO. Si bien el uso de GOTO puede hacer posible situaciones de las que un lenguaje carece, el uso indiscriminado de éstas harían a un código muy difícil de entender y mantener.

Esto deriva en circunstancias especiales que se consideran a continuación:

GOTO envía del flujo fuera de una estructura de control De modo general GOTO tiene otro enemigo, y es que cuando opera dentro de otra estructura de control que guarda punteros en la pila, si hay una sentencia GOTO que sale de la estructura de control, fuerza a que se vacíe la pila con los punteros de retorno que mantenía la estructura. Esto requiere un chequeo constante de la sentencia GOTO en busca de si aparece o no dentro de una estructura de control (Véase la sección donde se compara GOTO con otras estructuras de control, más adelante en este mismo artículo), para determinar si debe o no retirar de la pila un puntero al que aparentemente no se retornará ya. Una razón para salir de una estructura de control usando GOTO, es que dicha estructura no provea otro mecanismo de salida que llegar al final del bloque de sentencias que contiene la estructura, por lo que los diversos lenguajes han provisto una salida alternativa que solucione la operación que realiza GOTO en dichos casos y a su vez no requiere la verificación que se hacía precisa para cada GOTO, típicamente las sentencias de escape alternativas se han dado en llamar: Para las estructura de control que no requieren punto de retorno. Exit flujo donde flujo es la estructura de control, tales como DO, FOR, etc. Para las estructuras de control que requieren un punto de retorno, RETURN, tales como GOSUB, FUNCTION, etc..

Las sentencias EXIT, todavía están limitadas respecto de GOTO, pues EXIT siempre devuelve a la siguiente instrucción al final de la estructura de control.

Puede darse el caso en algunos lenguajes, que la ejecución de la sentencia GOTO no conlleve aparejado comprobar si salta fuera de una estructura de control y consecuentemente no elimine de la pila el puntero de retorno que se colocó al entrar a la rutina en dicho caso, a efectos del programa el control sigue dentro de dicha estructura y sigue esperando que alcance el final para volver al punto de retorno y vaciar la pila del valor de retorno, como esto ya no va a ocurrir, se está perdiendo espacio de pila con cada situación de este tipo. También podría darse el caso si algún lenguaje olvida aportar solución que al ir entregando desde la pila los sucesivos retornos, se apunte a un lugar diferente de la que el programador esperaba, por la cascada de entradas fue una y la cascada de salidas debiendo ser en orden inversa conserva una salida que nunca se va a producir, falsificando con ello todas las devoluciones anteriores a esa que se ha quedado perdida por la instrucción goto. Un modo en que algunos lenguajes solventan este problema es utilizando una pila exclusivamente local y eliminarla cuando se sale del procedimiento local, en dicho caso la dirección de retorno se guarda en una pila de ámbito mayor. Si hay punteros remanentes en la pila local no devueltos no producirán errores en cascada hacia atrás.

En situaciones así es difícil seguir la pista de saltos esperada respecto de la que el programador pretendiera hacer si no se comporta como él esperaba. También de este modo es posible hacer que el código se comporte de una forma que el lenguaje no tenía previsto en su diseño y aprovechar con ello una posible situación eficiente, para realizar determinadas tareas.

Adicionalmente para solventar los posibles problemas que el inadecuado uso de GOTO pueda originar, los lenguajes de alto nivel y que utilizan programación mediante bloques y módulos bien definidos y aislados, no permiten sobre GOTO más que operar dentro del bloque o módulo donde se aloja. Un caso típico son las modernas funciones FUNCTION, PROPERTY, etc. donde si bien un GOTO puede aparecer, no puede direccionar a un punto dentro de otra FUNCTION. No confundir este aislamiento con encapsulamiento, aunque la idea es la misma.

GOTO envía el flujo dentro de una estructura de control Sucede de otra forma cuando un salto por GOTO nos introduce dentro de una estructura de control. Si hay instrucciones tras la etiqueta a la que se salta, éstas se ejecutan correctamente, pero al llegar a una instrucción del final, si la pila está vacía (cuando la estructura de control requiere un puntero de retorno), ocurre un error que según el lenguaje varía, y si la pila no está vacía salta a la dirección que señala el último puntero en la pila, puede considerarse un error si no era lo que perseguía el programador, toda vez que dicho puntero no fue almacenado por dicha estructura decontrol en la que se halla sino por la previa.

Esto solo sucede en aquellas estructuras de control que guardan algún puntero de retorno en la pila, por ejemplo nunca ocurrirá un error dentro de una estructura IF...THEN, ni dentro de una estructura SELECT CASE (Switch), ni DO...LOOP ya que dichas estructuras al no tener al final un punto de retorno, no necesitan almacenar en la pila dicho punto de retorno.

Normalmente, es el caso que en los lenguajes, la ejecución de la sentencia GOTO no conlleva aparejado comprobar si salta dentro de una estructura de control, ya que en principio no debe generar errores aunque tenga un puntero de retorno siempre que este puntero esté localizado en la sentencia de salida en vez de en la pila.

Se detallan, comentados 3 casos comunes:

Caso de estructura de control donde el puntero de retorno se almacena en la sentencia final: este suele ser DO...LOOP, loop es equivalente a un GOTO DO. En una sección del artículo más adelante, se provee una implementación de la estructura de control DO...LOOP usando GOTO, que ayudará a entender este caso. En este caso por tanto saltar dentro de una estructura DO..LOOP no proporcionará un error si se llega a la sentencia final. (ver sección anterior). El puntero de retorno de esta estructura siempre apunta al principio de la estructura, es por esto que no necesita mantenerlo en la pila t resulta suficiente con dejarlo en la sentencia final.