Esiste un collezionista che effettua la raccolta in un set di conservazione degli ordini?


107

Collectors.toSet()non preserva l'ordine. Potrei invece usare Liste, ma voglio indicare che la raccolta risultante non consente la duplicazione degli elementi, che è esattamente a cosa Setserve l'interfaccia.


Non credo che esista una cosa del genere. So che ne avevo bisogno anche io e dovevo scriverne uno mio.
markspace

Funzionerebbe SortedSet? In caso contrario, l'abitudine è la strada da percorrere.
AntonH

@AntonH No, preferirei le operazioni O (1) a O (log n).
gvlasov

1
Ho pubblicato quel codice, non è esattamente ciò di cui hai bisogno, ma potrebbe aiutarti a iniziare.
markspace

Risposte:


203

Puoi usare toCollectione fornire l'istanza concreta del set che desideri. Ad esempio, se desideri mantenere l'ordine di inserzione:

Set<MyClass> set = myStream.collect(Collectors.toCollection(LinkedHashSet::new));

Per esempio:

public class Test {    
    public static final void main(String[] args) {
        List<String> list = Arrays.asList("b", "c", "a");

        Set<String> linkedSet = 
            list.stream().collect(Collectors.toCollection(LinkedHashSet::new));

        Set<String> collectorToSet = 
            list.stream().collect(Collectors.toSet());

        System.out.println(linkedSet); //[b, c, a]
        System.out.println(collectorToSet); //[a, b, c]
    }
}

Bello, è esattamente ciò di cui ho bisogno, ma penso che Guava ImmutableSetsarebbe ancora meglio nel mio caso. Qualche idea su come posso fare un collezionista che raccoglie a ImmutableSet? Le sue istanze sono costruite con un ImmutableSet.Builderche non è a Collection, quindi non riesco a capire come faresti Suppliera Collectors.toCollection()in quel caso.
gvlasov

@Susei cercherò di esaminarlo. Un'alternativa sarebbe restituire un set non modificabile. Es:Set<String> linkedSet = list.stream().collect(Collectors.toCollection(LinkedHashSet::new)); linkedSet = Collections.unmodifiableSet(linkedSet);
Alexis C.

@Susei Il più vicino che ho trovato: Set<String> set = list.stream().collect( ImmutableSet.Builder<String>::new, ImmutableSet.Builder<String>::add, (builder1, builder2) -> builder1.addAll(builder2.build())).build();non sono sicuro che sia un approccio migliore avvolgendo il set risultante con Collections.unmodifiableSet.
Alexis C.

Ecco una domanda dedicata dal momento che è già off-topic (e per ulteriori rappresentante per grandi risposte, ovviamente): stackoverflow.com/questions/27612165/...
gvlasov
Utilizzando il nostro sito, riconosci di aver letto e compreso le nostre Informativa sui cookie e Informativa sulla privacy.
Licensed under cc by-sa 3.0 with attribution required.