java compiler-construction

java - Error de compilador de código inalcanzable



compiler-construction (7)

¿Romperá el código de bytes de Java de alguna manera, es para proteger al programador o es otra cosa?

Esto no es necesario en lo que respecta a Java / JVM. El único propósito de este error de compilación es evitar los errores tontos del programador. Considere el siguiente código de JavaScript:

function f() { return { answer: 42 } }

Esta función devuelve undefined ya que el motor de JavaScript agrega un punto y coma al final de la línea e ignora el código muerto (como se cree). El compilador de Java es más inteligente y cuando descubre que estás haciendo algo claramente y obviamente mal, no te permitirá hacer esto. No hay manera en la tierra que quisieras tener un código muerto. Esto encaja de alguna manera en la premisa de Java de ser un lenguaje seguro.

Esta pregunta ya tiene una respuesta aquí:

El siguiente código da un error de compilador de unreachable statement

public static void main(String[] args) { return; System.out.println("unreachable"); }

A veces, para propósitos de prueba, queremos evitar que se llame a un método, por lo que una forma rápida de hacerlo (en lugar de comentarlo en cualquier lugar que se use) es regresar inmediatamente del método para que el método no haga nada. Lo que siempre hago para ubicar el error del compilador es esto

public static void main(String[] args) { if (true) { return; } System.out.println("unreachable"); }

Sólo tengo curiosidad, ¿por qué es un error del compilador? ¿Romperá el código de bytes de Java de alguna manera, es para proteger al programador o es otra cosa?

También (y esto para mí es más interesante), si compilar java a bytecode hace algún tipo de optimización (o incluso si no lo hace), ¿por qué no detecta el código descarado descarado en el segundo ejemplo? ¿Cuál sería el pseudo código del compilador para verificar si una declaración es inalcanzable?


El código inalcanzable no tiene sentido, por lo que el error en tiempo de compilación es útil. La razón por la que no se detectará en el segundo ejemplo es, como usted espera, con fines de prueba / depuración. Se explica en la especificación:

if (false) { x=3; }

no da lugar a un error en tiempo de compilación. Un compilador optimizador puede darse cuenta de que la instrucción x = 3; nunca se ejecutará y puede optar por omitir el código para esa declaración del archivo de clase generado, pero la instrucción x = 3; no se considera "inalcanzable" en el sentido técnico especificado aquí.

El fundamento de este tratamiento diferente es permitir que los programadores definan "variables de bandera" como:

static final boolean DEBUG = false;

y luego escribir código como:

if (DEBUG) { x=3; }

La idea es que debería ser posible cambiar el valor de DEBUG de falso a verdadero o de verdadero a falso y luego compilar el código correctamente sin otros cambios en el texto del programa.

Referencia: http://docs.oracle.com/javase/specs/jls/se8/html/jls-14.html#jls-14.21


En el primer caso, regresará antes de cualquier declaración, ya que el compilador nunca ejecutará ese código.

En el segundo código he puesto la declaración anterior de devolución y su trabajo ahora :)

La razón detrás de esto es que si regresa en algún momento, el código después de que nunca se ejecutará porque ya devolvió los datos de la función y como tal, se muestra un código inalcanzable.

public static void main (String [] args) {

return; System.out.println("unreachable");

}

///////////////////////////////////

public static void main (String [] args) {

System.out.println("unreachable"); // Put the statement before return return;

}


Es porque el escritor del compilador asumió que el humano en los controles es tonto, y probablemente no tuvo la intención de agregar código que nunca se ejecutaría, por lo que al lanzar un error, intenta evitar que se cree involuntariamente una ruta de código que no pueda ser ejecutada. ejecutado: en su lugar, lo obliga a tomar una decisión al respecto (aunque, como ha demostrado, aún puede solucionarlo).


Es porque es un desperdicio de recursos para que incluso esté allí. Además, los diseñadores del compilador no quieren asumir lo que pueden eliminar, sino que lo obligarán a eliminar el código que lo hace inalcanzable o el código inalcanzable en sí mismo. Ellos no saben lo que se supone que debe estar allí. Hay una diferencia entre las optimizaciones en las que modifican su código para que sean un poco más eficientes cuando se compila en el código de la máquina y simplemente elimina el código "que no era necesario".


Este error se produce principalmente para evitar errores de programación (un intercambio de 2 líneas o más). En el segundo fragmento, dejas claro que no te importa el sistema.out.println ().