instalar - ¿Hay algún ejemplo específico de incompatibilidades hacia atrás entre las versiones de Java?
java 7 download 32 bit (14)
Cada lanzamiento de Swing nos rompió algo, desde 1.3 hasta 1.6.
El problema de JDBC ya se mencionó, pero el código existente funcionó.
De 1.5 a 1.6 hubo un cambio en el comportamiento de Socket que rompió el cliente de Cisco.
Por supuesto, se introdujeron nuevas palabras clave reservadas.
El más grande que creo que fue verdaderamente imperdonable por parte de Sun fue System.getenv (). Funcionó en 1.0, y luego fue desaprobado y cambiado para arrojar un error en todas las plataformas bajo la justificación bastante dudosa de que Mac no tenía variables de entorno del sistema. Luego, la Mac obtuvo las variables de entorno del sistema, por lo que en 1.5 no fue procesada y funciona. No hay una justificación razonable para hacer eso. Devuelve un conjunto vacío en una Mac (Swing tiene problemas multiplataforma mucho más grandes si quieres preocuparte por ese nivel de consistencia multiplataforma) o incluso en todas las plataformas.
Nunca estuve de acuerdo con que apagaran la función, pero cambiarla para arrojar un error era solo un cambio radical que si lo hicieran, deberían haber eliminado completamente el método.
Pero, realmente de 1.0 a 1.1, estaban menos preocupados por la compatibilidad con versiones anteriores. Por ejemplo, eliminaron "privado protegido" como un modificador.
Entonces, el resultado es que cada versión cambia lo suficiente como para requerir una evaluación cercana, es por eso que todavía se ven muchas preguntas de 1.4 aquí en SO.
¿Ha habido incompatibilidades entre los lanzamientos de Java donde el código fuente de Java / los archivos de la clase Java dirigidos a la versión X de Java no se compilarán / ejecutarán en la versión Y (donde Y> X)?
Por "versión Java" me refiero a versiones como:
- JDK 1.0 (enero de 1996)
- JDK 1.1 (febrero de 1997)
- J2SE 1.2 (diciembre de 1998)
- J2SE 1.3 (mayo de 2000)
- J2SE 1.4 (febrero de 2002)
- J2SE 5.0 (septiembre de 2004)
- Java SE 6 (diciembre de 2006)
Reglas de casa:
- Por favor incluya referencias y ejemplos de código donde sea posible.
- Por favor, intenta ser muy específico / concreto en tu respuesta.
- Una clase que se marca como @Deprecated no cuenta como una incompatibilidad hacia atrás.
Como dijo Sean Reilly, un nuevo método puede romper tu código. Además del caso simple de que tienes que implementar un nuevo método (esto generará una advertencia del compilador), hay un peor caso: un nuevo método en la interfaz tiene la misma firma que un método que ya tienes en tu clase. La única pista del compilador es una advertencia de que @Override
anotación @Override
(Java 5 para las clases, la anotación es compatible con las interfaces en Java 6 pero es opcional).
Consulte el informe sobre los cambios de la API para la biblioteca de clases de JRE aquí: http://abi-laboratory.pro/java/tracker/timeline/jre/
El informe incluye un análisis de compatibilidad de fuente y binario hacia atrás de las clases de Java.
El informe es generado por la japi-compliance-checker .
...
Otro análisis interesante para JDK 1.0-1.6 lo puede encontrar en la página Japitools JDK-Results .
El principal que puedo pensar es la introducción de nuevas palabras reservadas:
Java 1.3: strictfp
Java 1.4: assert
Java 5.0: enum
Cualquier código que haya utilizado previamente estos valores como identificadores no se compilará en una versión posterior.
Otro problema que recuerdo que causó problemas en un proyecto en el que trabajé fue que había un cambio en la visibilidad predeterminada de JInternalFrames entre 1.2 y 1.3 . Estaban visibles de forma predeterminada, pero cuando lo actualizamos a 1.3 todos parecían haber desaparecido.
En primer lugar, Sun realmente considera que todos los lanzamientos que mencionaste (aparte de 1.0 por supuesto) son versiones menores , no importantes.
No conozco ningún ejemplo de incompatibilidad binaria en ese momento. Sin embargo, ha habido algunos ejemplos de incompatibilidad de fuentes:
En Java 5, "enum" se convirtió en una palabra reservada; no fue antes Por lo tanto, había archivos fuente que usaban enum como un identificador que se compilaría en Java 1.4 que no se compilaría en Java 5.0. Sin embargo, puede compilar con -ource 1.4 para evitar esto.
Agregar métodos a una interfaz también puede romper la compatibilidad de la fuente. Si implementa una interfaz y luego intenta compilar esa implementación con un JDK que agregue nuevos métodos a la interfaz, el archivo fuente ya no se compilará correctamente, porque no implementa todos los miembros de la interfaz. Esto ha sucedido frecuentemente con java.sql.Statement y las otras interfaces jdbc. Las formas compiladas de estas implementaciones "inválidas" seguirán funcionando a menos que realmente llame a uno de los métodos que no existe; si haces eso, se lanzará una MissingMethodException.
Estos son algunos ejemplos que puedo recordar de la parte superior de mi cabeza, puede haber otros.
Entre 1.3 y 1.4, la interpretación de Long.parseLong (String) manejó la cadena vacía de manera diferente. 1.3 devuelve un valor 0
, mientras que 1.4 arroja una NumberFormatException
.
No es necesario recompilar, pero el código de trabajo dejó de funcionar si dependía del comportamiento 1.3.
La interfaz java.sql.Connection
se extendió desde Java 1.5 a Java 1.6 haciendo que la compilación de todas las clases que implementaron esta interfaz falle.
La semántica del modelo de memoria cambió de 1.4 a 1.5 . Fue cambiado para permitir, además de otras cosas, verificar nuevamente el bloqueo. (Creo que la semántica volátil se corrigió). Estaba roto.
Lo siguiente se compilará bajo Java 1.4 pero no con Java 1.5 o posterior.
(Java 5 introdujo ''enum'' como palabra clave. Nota: se compilará en Java 5 si se proporciona la opción "-ource 1.4").
public class Example {
public static void main(String[] args) {
String enum = "hello";
}
}
No lo he intentado, pero en teoría esto funcionaría en Java 1.1 y rompería en Java 1.2. (Más información aquí )
public class Test {
float strictfp = 3.1415f;
}
Obviamente, la convención de nomenclatura de los nombres de las versiones no es compatible con versiones anteriores .
- JDK 1.0 (23 de enero de 1996)
- JDK 1.1 (19 de febrero de 1997)
- J2SE 1.2 (8 de diciembre de 1998)
- J2SE 1.3 (8 de mayo de 2000)
- J2SE 1.4 (6 de febrero de 2002)
- J2SE 5.0 (30 de septiembre de 2004)
- Java SE 6 (11 de diciembre de 2006)
- Actualización de Java SE 6, actualización 12, actualización 14, actualización 16
- Java SE 7 ??? JDK7?
Otro ejemplo más de la compatibilidad de ruptura de java.sql:
En 1.5, se agregó un método compareTo (Date) a java.sql.Timestamp. Este método lanzaría una ClassCastException si la Fecha proporcionada no era una instancia de java.sql.Timestamp. Por supuesto, java.sql.Timestamp extiende Date, y Date ya tenía un método compareTo (Fecha) que funcionaba con todas las fechas, por lo que significaba que el código que comparaba una marca de tiempo con una fecha (non-Timestamp) se rompería en tiempo de ejecución en 1.5 .
Es interesante observar que parece que 1.6 parece haber solucionado este problema. Mientras que la documentación para java.sql.Timestamp.compareTo (Date) aún dice "Si el argumento no es un objeto Timestamp
, este método arroja un objeto ClassCastException
", la implementación actual dice lo contrario. Creo que esto es un error de documentación.
Por experiencia personal, tuvimos algunos campos de texto AWT / Swing incrustados en un marco SWT_AWT en 1.5, que dejaron de ser editables después de actualizar a 1.6.