Pregunta

Tengo que usar Java 1.4 y estoy usando estructuras ArrayList. Ahora necesito hacer una reactiva y ayudaría si puedo usar genéricos. Actualmente tengo código como este

ArrayList rows = new ArrayList();

Que es una lista de matrices sencilla. Pero ahora la variable de "filas" se está volviendo más compleja y necesita definir una clase de "fila". Ahora quiero hacer algo como lo que ves en J2SE 1.5

ArrayList<Row> rows = new ArrayList();

Un arrastre a través de Google no expone ninguna respuesta sin un uso sofisticado de soluciones de terceros. ¿Cómo tendría que cambiar mi código para acomodar esto en 1.4, sin usar soluciones de terceros/proyectos de código abierto (si es posible)?

¿Fue útil?

Solución

Los genéricos se introdujeron en JDK 1.5. Entonces no puedes usarlos en 1.4. Sin embargo, es posible que pueda usar el compilador JDK 1.5 pero apuntar 1.4 con sus clases con -target 1.4 opción Javac mientras mantiene -source 1.5 opción para indicar que su fuente es 1.5 compatible. En este caso, puede usar genéricos, ya que no deben afectar las clases de resultados.

Consulte la sección sobre opciones de compilación cruzada

Otros consejos

Los genéricos tienden a abordar el problema de lo que considero "ingenuo se coloca" en Java 1.4 o antes cuando se trata de colecciones. En Java 1.5+, la línea que ha colocado:

ArrayList<Row> rows = new ArrayList();

daría una advertencia, el código genérico adecuado es

ArrayList<Row> rows = new ArrayList<Row>();

Esto le dice al compilador que su objeto ArrayList solo debe contener el tipo de fila.

Sin embargo, dado que Java 1.5 es compatible con al revés con enormes conjuntos de bibliotecas que no contienen esa sintaxis, sino su código anterior:

ArrayList rows = new ArrayList();

Los genéricos obviamente no funcionarían con estas bibliotecas más antiguas; por lo tanto, los genéricos son solo un tiempo de compilación Opción: las clases 1.5 y 1.4 son efectivamente equivalentes (menos cualquier refactorización interna/nuevos métodos agregados más adelante) porque realmente son implementaciones de listas de matriz que manejan cualquier tipo de objeto.

El código 1.5 simplemente agrega en un elenco directo para usted.

En el código 1.4, digamos que quería iterar sobre ArrayList. La ingenua forma de hacer esto es lo siguiente:

for(Iterator rowIterator = rows.iterator(); rowIterator.hasNext(); ) {
    Row row = (Row) rowIterator.next();
    // Do something with the row.
}

El código de Java 1.5 es exactamente equivalente a la versión de reparto ingenuo. Se necesita el hecho de que le estás diciendo al compilador que es una fila y hace ese código para ti. Por lo tanto, los beneficios de azúcar sintáctico son más agradables (esto usa el más nuevo para cada sintaxis de bucle, pero genera el mismo código que el bucle anterior):

for(Row row : rows) {
   // Do something with the row
}

Entonces, si desea usar una lista de matrices que contenga solo filas, aún puede. Pero no hay forma de que el compilador controlar que la ArrayList contiene solo todas las filas (aunque, aunque el compilador proporciona esta verificación, es aun posible Para enviar una lista de matrices que contenga otros tipos de objetos, ya que, nuevamente, ArrayList todavía solo maneja el tipo de objeto, y los genéricos se borran en tiempo de ejecución; todo lo que queda es el código de reparto ingenuo que ya no ve) .

La variante no NAIVE es verificar cada instancia y lanzar una ClassCastException usted mismo con un mensaje informativo (en lugar de que el programa lance uno con su mensaje predeterminado):

for(Iterator rowIterator = rows.iterator(); rowIterator.hasNext(); ) {
    Object shouldBeRow = rowIterator.next();
    if(!(shouldBeRow instanceof Row)) {
        throw new ClassCastException("The object " + shouldBeRow + " is not an instance of Row - only Rows should be present in the list!");
    }
    Row row = (Row) shouldBeRow;
    // Do something with the row.
}

Sin embargo, en general, nadie hace esto: una buena documentación puede hacer que este problema sea discutible, ya que coloca la carga de proporcionar la colección correcta en la persona que llama y, por lo tanto, puede que el JVM sea lanzada por el JVM.

Sí tu puedes. Use un compilador 1.5 y use

javac -target jsr14 ............

Esto generará clases Java 1.4, pero permitirá genéricos.

Este interruptor solo se puede utilizar para el código no byte visible 1.5 características. Por ejemplo, no puede usar enums, o nuevos métodos introducidos en 1.5. Pero los genéricos están bien, ya que realmente no están presentes en el código de byte.

No, no puedes usarlos en JDK 1.4. Fueron introducidos en JDK1.5

Todo lo que tienes que hacer es elegirlos. Esto podría merecer una excepción de tiempo de ejecución si pone los tipos "incorrectos" en la lista.

Row arow = (Row) rows.get(0);

for ($i=0; i<rows.size(); $i++){
    Row element = (Row) rows.get($i);
    element.printCells();
    (...)
}
Licenciado bajo: CC-BY-SA con atribución
No afiliado a StackOverflow
scroll top