utilizar una sort por ordenar ordenada orden objetos metodo lista fechas enteros crear como array alfabetico alfabeticamente java collections

sort - Iterando a través de una lista en orden inverso en java



ordenar un array java (15)

Estoy migrando una pieza de código para hacer uso de los genéricos. Un argumento para hacerlo es que el bucle for es mucho más limpio que el seguimiento de índices o el uso de un iterador explícito.

En aproximadamente la mitad de los casos, la lista (una ArrayList) se está iterando en orden inverso utilizando un índice en la actualidad.

¿Puede alguien sugerir una forma más limpia de hacer esto (ya que no me gusta el indexed for loop cuando se trabaja con colecciones), aunque funciona?

for (int i = nodes.size() - 1; i >= 0; i--) { final Node each = (Node) nodes.get(i); ... }

Nota: No puedo agregar nuevas dependencias fuera del JDK.


Aquí hay una implementación (no probada) de un ReverseIterable . Cuando se llama a hasNext() , crea y devuelve una implementación privada ReverseIterator , que simplemente asigna las llamadas a hasNext() a hasPrevious() y las llamadas a next() se asignan a previous() . Significa que podría iterar sobre un ArrayList a la inversa de la siguiente manera:

ArrayList<String> l = ... for (String s : new ReverseIterable(l)) { System.err.println(s); }

Definición de clase

public class ReverseIterable<T> implements Iterable<T> { private static class ReverseIterator<T> implements Iterator { private final ListIterator<T> it; public boolean hasNext() { return it.hasPrevious(); } public T next() { return it.previous(); } public void remove() { it.remove(); } } private final ArrayList<T> l; public ReverseIterable(ArrayList<T> l) { this.l = l; } public Iterator<T> iterator() { return new ReverseIterator(l.listIterator(l.size())); } }


Como se ha sugerido al menos dos veces, puede usar descendingIterator con un Deque , en particular con un LinkedList . Si desea usar el bucle for-each (es decir, tener un Iterable ), puede construir y usar un enrollador como este:

import java.util.*; public class Main { public static class ReverseIterating<T> implements Iterable<T> { private final LinkedList<T> list; public ReverseIterating(LinkedList<T> list) { this.list = list; } @Override public Iterator<T> iterator() { return list.descendingIterator(); } } public static void main(String... args) { LinkedList<String> list = new LinkedList<String>(); list.add("A"); list.add("B"); list.add("C"); list.add("D"); list.add("E"); for (String s : new ReverseIterating<String>(list)) { System.out.println(s); } } }


Crea un reverseIterable personalizado.


Ejemplo muy simple:

List<String> list = new ArrayList<String>(); list.add("ravi"); list.add("kant"); list.add("soni"); // Iterate to disply : result will be as --- ravi kant soni for (String name : list) { ... } //Now call this method Collections.reverse(list); // iterate and print index wise : result will be as --- soni kant ravi for (String name : list) { ... }


Esta es una pregunta antigua, pero carece de una respuesta fácil para java8. Aquí hay algunas formas de revertir la lista, con la ayuda de la API de transmisión:

List<Integer> list = new ArrayList<Integer>(Arrays.asList(1, 3, 3, 7, 5)); list.stream().forEach(System.out::println); // 1 3 3 7 5 int size = list.size(); ListIterator<Integer> it = list.listIterator(size); Stream.generate(it::previous).limit(size) .forEach(System.out::println); // 5 7 3 3 1 ListIterator<Integer> it2 = list.listIterator(size); Stream.iterate(it2.previous(), i -> it2.previous()).limit(size) .forEach(System.out::println); // 5 7 3 3 1 // If list is RandomAccess (i.e. an ArrayList) IntStream.range(0, size).map(i -> size - i - 1).map(list::get) .forEach(System.out::println); // 5 7 3 3 1 // If list is RandomAccess (i.e. an ArrayList), less efficient due to sorting IntStream.range(0, size).boxed().sorted(Comparator.reverseOrder()) .map(list::get).forEach(System.out::println); // 5 7 3 3 1


Motivo: "No sé por qué no hay un Iterator descendente con ArrayList ..."

Dado que la lista de matrices no mantiene la lista en el mismo orden en que se agregaron los datos a la lista. Por lo tanto, nunca utilice Arraylist.

La lista enlazada mantendrá los datos en el mismo orden de AGREGAR a la lista.

Entonces, arriba en mi ejemplo, utilicé ArrayList () para hacer que el usuario retorciera su mente y ejercitara algo de su lado.

En lugar de esto

List<String> list = new ArrayList<String>();

UTILIZAR:

List<String> list = new LinkedList<String>(); list.add("ravi"); list.add("kant"); list.add("soni"); // Iterate to disply : result will be as --- ravi kant soni for (String name : list) { ... } //Now call this method Collections.reverse(list); // iterate and print index wise : result will be as --- soni kant ravi for (String name : list) { ... }


No creo que sea posible usar la sintaxis de bucle for. Lo único que puedo sugerir es hacer algo como:

Collections.reverse(list); for (Object o : list) { ... }

... pero no diría que esto es "más limpio" dado que va a ser menos eficiente.


Opción 1: ¿Ha pensado en revertir la Lista con Collections#reverse() y luego usar foreach?

Por supuesto, es posible que también desee refactorizar su código de manera que la lista se ordene correctamente para que no tenga que revertirlo, lo que requiere espacio / tiempo adicional.

EDITAR:

Opción 2: Alternativamente, ¿podría usar un Deque lugar de un ArrayList? Te permitirá iterar hacia adelante y hacia atrás.

EDITAR:

Opción 3: como otros han sugerido, puede escribir un iterador que repasará la lista a la inversa, aquí hay un ejemplo:

import java.util.Iterator; import java.util.List; public class ReverseIterator<T> implements Iterator<T>, Iterable<T> { private final List<T> list; private int position; public ReverseIterator(List<T> list) { this.list = list; this.position = list.size() - 1; } @Override public Iterator<T> iterator() { return this; } @Override public boolean hasNext() { return position >= 0; } @Override public T next() { return list.get(position--); } @Override public void remove() { throw new UnsupportedOperationException(); } } List<String> list = new ArrayList<String>(); list.add("A"); list.add("B"); list.add("C"); list.add("D"); list.add("E"); for (String s : new ReverseIterator<String>(list)) { System.out.println(s); }


Para tener un código que se ve así:

List<Item> items; ... for (Item item : In.reverse(items)) { ... }

Coloque este código en un archivo llamado "In.java":

import java.util.*; public enum In {; public static final <T> Iterable<T> reverse(final List<T> list) { return new ListReverseIterable<T>(list); } class ListReverseIterable<T> implements Iterable<T> { private final List<T> mList; public ListReverseIterable(final List<T> list) { mList = list; } public Iterator<T> iterator() { return new Iterator<T>() { final ListIterator<T> it = mList.listIterator(mList.size()); public boolean hasNext() { return it.hasPrevious(); } public T next() { return it.previous(); } public void remove() { it.remove(); } }; } } }



Podría usar la clase concreta LinkedList lugar de la List interfaz general. Entonces tienes un Iterator descendingIterator para iterar con la dirección inversa.

LinkedList<String > linkedList; for( Iterator<String > it = linkedList.descendingIterator(); it.hasNext(); ) { String text = it.next(); }

No sé por qué no hay un ArrayList descendingIterator con ArrayList ...


Prueba esto:

// Substitute appropriate type. ArrayList<...> a = new ArrayList<...>(); // Add elements to list. // Generate an iterator. Start just after the last element. ListIterator li = a.listIterator(a.size()); // Iterate in reverse. while(li.hasPrevious()) { System.out.println(li.previous()); }


Si las listas son bastante pequeñas para que el rendimiento no sea un problema real, se puede usar el método reverse de las Lists clase en Google Guava . Rinde bastante for-each código, y la lista original permanece igual. Además, la lista invertida está respaldada por la lista original, por lo que cualquier cambio en la lista original se reflejará en la reversa.

import com.google.common.collect.Lists; [...] final List<String> myList = Lists.newArrayList("one", "two", "three"); final List<String> myReverseList = Lists.reverse(myList); System.out.println(myList); System.out.println(myReverseList); myList.add("four"); System.out.println(myList); System.out.println(myReverseList);

Rinde el siguiente resultado:

[one, two, three] [three, two, one] [one, two, three, four] [four, three, two, one]

Lo que significa que la iteración inversa de myList se puede escribir como:

for (final String someString : Lists.reverse(myList)) { //do something }


También se encuentra el método reverse colecciones de Google


Guava ofrece Lists#reverse(List) e ImmutableList#reverse() . Como en la mayoría de los casos para Guayaba, los antiguos delegados a los últimos si el argumento es una ImmutableList , por lo que puede usar los primeros en todos los casos. Estas no crean nuevas copias de la lista sino simplemente "vistas invertidas" de la lista.

Ejemplo

List reversed = ImmutableList.copyOf(myList).reverse();