2011-05-31 18 views
24

Tengo este extraño problema (creo) en Java. Tengo un ArrayList y quiero tomar una sublista. Pero obtengo la siguiente excepción.¿Cómo tomar una sublista válida en Java?

package javatest; 

import java.util.ArrayList; 

public class JavaTest { 

    public static void main(String[] args) { 
     ArrayList<Integer> alist = new ArrayList<Integer>(); 
     alist.add(10); 
     alist.add(20); 
     alist.add(30); 
     alist.add(40); 
     alist.add(50); 
     alist.add(60); 
     alist.add(70); 
     alist.add(80); 
     ArrayList<Integer> sub = (ArrayList<Integer>) alist.subList(2, 4); 
     for (Integer i : sub) 
      System.out.println(i); 
    } 
} 

de ejecución: Excepción en el hilo "principal" java.lang.ClassCastException: java.util.RandomAccessSubList no se puede convertir a java.util.ArrayList en javatest.JavaTest.main (JavaTest. java: 17) Java Resultado: 1

¿Cuál es la forma correcta de tomar una sublista?

Thx

+1

Se adhieren a la lista de interfaz, no a la Implementación y estarán bien. Compruebe la respuesta por cero. –

Respuesta

23

Debe trabajar con las interfaces para las colecciones siempre que sea posible. Está descifrando el resultado de la sublista, pero la API especifica que devuelve List (noArrayList). Aquí, los implementadores eligen devolver un tipo diferente para facilitarles la vida.

Además, la documentación de la API especifica que la sublista devolverá una lista mapeada en el original, ¡así que ten cuidado!

+5

Solo esperaba que una sublista de FooList también sea una Foolista. Creo que es lo razonable de pensar. De todos modos thx :) –

8

Prueba esto ...

List<Integer> alist = new ArrayList<Integer>(); 
alist.add(10); 
alist.add(20); 
alist.add(30); 
alist.add(40); 
alist.add(50); 
alist.add(60); 
alist.add(70); 
alist.add(80); 
List<Integer> sub = alist.subList(2, 4); 
for (Integer i : sub) 
    System.out.println(i); 
+1

El elenco no es necesario. – helpermethod

+0

@Helper Método: gracias, fijo :) –

3

Trate

List<Integer> sub = alist.subList(2, 4); 
0

Cambiar el código para:

List<Integer> sub = alist.subList(2, 4); 

El método devuelve un sublist()List, que no necesariamente es un ArrayList (aquí en realidad es un RandomAccessSublist, por lo que el elenco falla).

46

que sea lo más:

List sublist = new ArrayList(); 
sublist = new ArrayList<String>(alist.subList(2, 4)); 

y debería funcionar

+0

funciona como se esperaba, gracias –

+1

Esto es muy incorrecto. La primera línea no tiene ningún efecto. Crea una nueva lista de Array que queda huérfana en la línea siguiente cuando se crea una nueva ArraysList . La nueva ArrayList se inicializa con los valores devueltos por alist.subList. Pero esto es muy diferente de alist.subList que está respaldado por alist. –

2
public List<E> subList(int fromIndex, int toIndex) { 
    return (this instanceof RandomAccess ? 
      new RandomAccessSubList<E>(this, fromIndex, toIndex) : 
      new SubList<E>(this, fromIndex, toIndex)); 
    } 

como en impl del ArrayList, es Lista de retorno, ya que dicho uso interfaz siempre que sea posible @George Kastrinis.

Cuestiones relacionadas