web-dev-qa-db-fra.com

Tri d'une liste avec stream.sorted () dans Java

Je suis intéressé à trier une liste à partir d'un flux. C'est le code que j'utilise:

list.stream()
    .sorted((o1, o2)->o1.getItem().getValue().compareTo(o2.getItem().getValue()))
    .collect(Collectors.toList());

Est-ce que je manque quelque chose? La liste n'est pas en train de trier.

Il convient de trier les listes en fonction de l'élément avec la valeur la plus basse.

for (int i = 0; i < list.size(); i++)
{
   System.out.println("list " + (i+1));
   print(list, i);
}

Et la méthode d'impression:

public static void print(List<List> list, int i)
{
    System.out.println(list.get(i).getItem().getValue());
}
65
Ivan C

Ce n'est pas comme Collections.sort() où la référence de paramètre est triée. Dans ce cas, vous obtenez simplement un flux trié que vous devez collecter et affecter à une autre variable:

List result = list.stream().sorted((o1, o2)->o1.getItem().getValue().
                                   compareTo(o2.getItem().getValue())).
                                   collect(Collectors.toList());

Vous avez juste manqué d'assigner le résultat

113
Matt

Utilisez list.sort à la place:

_list.sort((o1, o2) -> o1.getItem().getValue().compareTo(o2.getItem().getValue()));
_

et le rendre plus succinct en utilisant Comparator.comparing :

_list.sort(Comparator.comparing(o -> o.getItem().getValue()));
_

Après l'un ou l'autre, list elle-même sera triée.

Votre problème est que list.stream.sorted renvoie les données triées, elles ne se trient pas à la place, attendant.

48
River

Java 8 fournit différentes méthodes API utilitaires pour nous aider à mieux trier les flux.

Si votre liste est une liste d'entiers (ou Double, Long, Chaîne, etc.), vous pouvez simplement trier la liste avec des comparateurs par défaut fournis par Java.

List<Integer> integerList = Arrays.asList(1, 4, 3, 4, 5);

Création d'un comparateur à la volée:

integerList.stream().sorted((i1, i2) -> i1.compareTo(i2)).forEach(System.out::println);

Avec le comparateur par défaut fourni par Java 8 lorsqu'aucun argument n'est transmis à sorted ():

integerList.stream().sorted().forEach(System.out::println); //Natural order

Si vous souhaitez trier la même liste dans l'ordre inverse:

integerList.stream (). trié (Comparator.reverseOrder ()). forEach (System.out :: println); // Ordre inverse

Si votre liste est une liste d'objets définis par l'utilisateur, alors:

List<Person> personList = Arrays.asList(new Person(1000, "First", 25, 30000),
        new Person(2000, "Second", 30, 45000),
        new Person(3000, "Third", 35, 25000));

Création d'un comparateur à la volée:

personList.stream().sorted((p1, p2) -> ((Long)p1.getPersonId()).compareTo(p2.getPersonId()))
        .forEach(person -> System.out.println(person.getName()));

Utilisation de la méthode Comparator.comparingLong () (Nous avons également des méthodes ComparisonDouble (), comparativeInt ()):

personList.stream().sorted(Comparator.comparingLong(Person::getPersonId)).forEach(person -> System.out.println(person.getName()));

Utilisation de la méthode Comparator.comparing () (méthode générique qui compare sur la base de la méthode getter fournie):

personList.stream().sorted(Comparator.comparing(Person::getPersonId)).forEach(person -> System.out.println(person.getName()));

Nous pouvons aussi faire du chaînage en utilisant la méthode thenComparing ():

personList.stream().sorted(Comparator.comparing(Person::getPersonId).thenComparing(Person::getAge)).forEach(person -> System.out.println(person.getName())); //Sorting by person id and then by age.

Classe de personne

public class Person {
    private long personId;
    private String name;
    private int age;
    private double salary;

    public long getPersonId() {
        return personId;
    }

    public void setPersonId(long personId) {
        this.personId = personId;
    }

    public Person(long personId, String name, int age, double salary) {
        this.personId = personId;
        this.name = name;
        this.age = age;

        this.salary = salary;
    }

    public String getName() {
        return name;
    }

    public void setName(String name) {
        this.name = name;
    }

    public int getAge() {
        return age;
    }

    public void setAge(int age) {
        this.age = age;
    }

    public double getSalary() {
        return salary;
    }

    public void setSalary(double salary) {
        this.salary = salary;
    }
}
Collection<Map<Item, Integer>> itemCollection = basket.values();
Iterator<Map<Item, Integer>> itemIterator =   itemCollection.stream().sorted(new TestComparator()).collect(Collectors.toList()).iterator();



package com.ie.util;

import com.ie.item.Item;

import Java.util.Comparator;
import Java.util.Iterator;
import Java.util.Map;
import Java.util.Set;

public class TestComparator implements Comparator<Map<Item, Integer>> {

// comparator is used to sort the Items based on the price


    @Override
    public int compare(Map<Item, Integer> o1, Map<Item, Integer> o2) {


      //  System.out.println("*** compare method will be called *****");


        Item item1 = null;
        Item item2 = null;


        Set<Item> itemSet1 = o1.keySet();
        Iterator<Item> itemIterator1 = itemSet1.iterator();
        if(itemIterator1.hasNext()){
           item1 =   itemIterator1.next();
        }

        Set<Item> itemSet2 = o2.keySet();
        Iterator<Item> itemIterator2 = itemSet2.iterator();
        if(itemIterator2.hasNext()){
            item2 =   itemIterator2.next();
        }


        return -item1.getPrice().compareTo(item2.getPrice());


    }
}

**** Ceci est utile pour trier les objets de carte imbriqués tels que Carte> ici, triés en fonction du prix de l'objet Article.

0

Cela semble bien fonctionner:

List<BigDecimal> list = Arrays.asList(new BigDecimal("24.455"), new BigDecimal("23.455"), new BigDecimal("28.455"), new BigDecimal("20.455"));
System.out.println("Unsorted list: " + list);
final List<BigDecimal> sortedList = list.stream().sorted((o1, o2) -> o1.compareTo(o2)).collect(Collectors.toList());
System.out.println("Sorted list: " + sortedList);

Exemple Entrée/Sortie

Unsorted list: [24.455, 23.455, 28.455, 20.455]
Sorted list: [20.455, 23.455, 24.455, 28.455]

Etes-vous sûr de ne pas vérifier la liste au lieu de sortedList [dans l'exemple ci-dessus], c.-à-d. Que vous stockez le résultat de stream() dans un nouvel objet List et que vous vérifiez cet objet?

0
Tanmay Baid