En Java, ¿por qué no funciona la siguiente línea de código?
List<List> myList = new ArrayList<ArrayList>();
Funciona si lo cambio a
List<ArrayList> myList = new ArrayList<ArrayList>();
Al principio, pensé que tal vez no puedas tener listas de una interfaz, pero puedo crear una List
muy bien.
Ideas?
Los tipos generics son más pedantes.
List
significa List
o cualquier subtipo, pero
significa solo List
. Si desea un subtipo, debe tener < ? extends List>
< ? extends List>
Sospecho que puedes usar
List> myList = new ArrayList
>();
La razón por la que no puede hacer esto es porque puede estar usando una referencia a una referencia y con un nivel adicional de indirección debe tener cuidado.
// with one level of indirection its simple. ArrayList alist = new ArrayList(); List list = aList; // all good list = new LinkedList(); // alist is still good.
Con los generics puede tener dos niveles de indirección que le pueden dar problemas para que sean más pedantes para evitar estos problemas.
// with two levels of indirection List alist = new ArrayList (); List list = (List) alist; // gives you a warning. list.add(new LinkedList()); // adding a LinkedList into a list of ArrayList!! System.out.println(alist.get(0)); // runtime error
huellas dactilares
Exception in thread "main" java.lang.ClassCastException: java.util.LinkedList cannot be cast to java.util.ArrayList
Comencemos con esto:
ArrayList> myList = new ArrayList >();
Esto está creando una ArrayList cuyos elementos son ArrayLists.
Ahora supongamos que podríamos asignar eso a
List> myList2 = myList.
Ahora, deberíamos poder hacer esto:
myList2.add(new LinkedList());
Pero eso significa que hemos agregado una LinkedList a una lista cuyos elementos se supone que son ArrayLists. Ooops!
En realidad, la asignación de myList
a myList2
no es legal … y eso asegura que no es posible agregar el tipo incorrecto de List
al objeto ArrayList
. (No Peter, no es solo pedantería :-))
Solo la colección de nivel superior puede declararse como una clase de implementación, mientras que las anidadas deben seguir siendo interfaces hasta que realmente cree instancias:
List> rootList = new ArrayList
>();
y luego cuando crea un elemento para entrar, lo convierte en una implementación:
List nodeList = new ArrayList (); rootList.add(nodeList);
Compara el Type
desde el lado izquierdo (statement) al Type
desde el lado derecho (instanciación). En la izquierda, su tipo es List
mientras que en la derecha, es ArrayList
. Si se queja de la diferencia.
Actualice el lado derecho (instatiación) como Lista, es decir,
List> myList = new ArrayList
>();
Esto debería funcionar bien.
Sé que esta es una vieja pregunta, pero solo quería compartir mi idea.
En lugar de hacer una lista de listas, personalmente hago una lista de tipos [] ( List
), genero una lista separada de simplemente tipo ( List
), luego .add(list.toArray())
. De esta manera, es más claro y fácil de leer que la syntax de la Lista de listas, que es confusa.
Por ejemplo, en un proyecto reciente donde tenía un archivo de entrada donde cada línea con solo un “0” significaba una nueva línea en el original (era un algoritmo de encriptación):
String[] input = getInputContents(inFile); List currentBuffer = new ArrayList (); List buffers = new ArrayList (); for(String line : input) { if(line.equals("0")) { buffers.add((String[])currentBuffer.toArray()); currentBuffer = new ArrayList (); } else { currentBuffer.add(line); } }
la list
está permitido si la lista contiene una lista más dentro de la lista. > l1=new list
>();
public final class CPanelXMLBuilder extends PanelXMLBuilder { public CPanelXMLBuilder(AuthenticatedUser pAuthenticatedUser, Map pSessionMap, Map pRequestMap, String pPanelTemplate) throws Exception { super(pAuthenticatedUser, pSessionMap, pRequestMap, pPanelTemplate, null); } public Map buildXMLDocument(List> pDetailsList) { if (pDetailsList.size() == 1) { List pCustomerDetail = pDetailsList.get(0); xmlDocument.getRootElement().getChild("E_SHOW1").setText(pCustomerDetail.get(0)); xmlDocument.getRootElement().getChild("E_SHOW2").setText(pCustomerDetail.get(1)); xmlDocument.getRootElement().getChild("E_SHOW3").setText(pCustomerDetail.get(2)); xmlDocument.getRootElement().getChild("E_SHOW4").setText(pCustomerDetail.get(3)); xmlDocument.getRootElement().getChild("E_SHOW5").setText(pCustomerDetail.get(4)); xmlDocument.getRootElement().getChild("ServerTimestamp").setText(pCustomerDetail.get(5).substring(0, 19)); } else { xmlDocument.getRootElement().getChild("AlertType").setText("INFO"); xmlDocument.getRootElement().getChild("Alert").setText("There is no matching record."); } requestMap.put(RequestMapKeys.XML_DOCUMENT, xmlDocument); return requestMap; } }