Filtrovanie a transformácia zbierok na Guave

1. Prehľad

V tomto výučbe si ukážeme, ako na to filtrujte a transformujte zbierky pomocou Guavy.

Filtrujeme pomocou Predikátov, transformujeme pomocou Funkcií, ktoré poskytuje knižnica a nakoniec uvidíme, ako kombinovať filtrovanie aj transformáciu.

2. Filtrujte zbierku

Začnime jednoduchým príkladom filtrovanie zbierky. Budeme používať predikát poskytnutý knižnicou a zostavený prostredníctvom Predikáty úžitková trieda:

@Test public void whenFilterWithIterables_thenFiltered () {List names = Lists.newArrayList ("John", "Jane", "Adam", "Tom"); Iterable result = Iterables.filter (names, Predicates.containsPattern ("a")); assertThat (result, containsInAnyOrder ("Jane", "Adam")); }

Ako vidíte, filtrujeme Zoznam mien dostávať iba mená, ktoré obsahujú znak „a“ - a my ich používame Iterables.filter () urobiť to.

Prípadne môžeme dobre využiť Collections2.filter () API tiež:

@Test public void whenFilterWithCollections2_thenFiltered () {List names = Lists.newArrayList ("John", "Jane", "Adam", "Tom"); Výsledok zbierky = Collections2.filter (names, Predicates.containsPattern ("a")); assertEquals (2, result.size ()); assertThat (result, containsInAnyOrder ("Jane", "Adam")); result.add ("anna"); assertEquals (5, names.size ()); }

Tu je treba poznamenať niekoľko vecí - najskôr výstup z Collections.filter () je živý pohľad na pôvodnú zbierku - zmeny v jednej sa prejavia v druhej.

Je tiež dôležité pochopiť, že teraz, výsledok je obmedzený predikátom - ak pridáme prvok, ktorý to nevyhovuje Predikát, an IllegalArgumentException bude vyhodené:

@Test (očakáva sa = IllegalArgumentException.class) public void givenFilteredCollection_whenAddingInvalidElement_thenException () {List names = Lists.newArrayList ("John", "Jane", "Adam", "Tom"); Výsledok zbierky = Collections2.filter (names, Predicates.containsPattern ("a")); result.add ("elvis"); }

3. Napíšte vlastný filter Predikát

Ďalej - napíšme si svoje Predikát namiesto použitia knižnice. V nasledujúcom príklade - definujeme predikát, ktorý dostane iba mená, ktoré začínajú na „A“ alebo „J“:

@Test public void whenFilterCollectionWithCustomPredicate_thenFiltered () {Predicate predicate = new Predicate () {@Override public boolean apply (String input) return input.startsWith ("A")}; Názvy zoznamu = Lists.newArrayList ("John", "Jane", "Adam", "Tom"); Výsledok zbierky = Collections2.filter (mená, predikát); assertEquals (3, result.size ()); assertThat (result, containsInAnyOrder ("John", "Jane", "Adam")); }

4. Spojte viac predikátov

Môžeme kombinovať viac predikátov pomocou Predicates.or () a Predicates.and ().

V nasledujúcom príklade - filtrujeme a Zoznam mien, aby ste dostali mená, ktoré začínajú na „J“ alebo neobsahujú „a“:

@Test public void whenFilterUsingMultiplePredicates_thenFiltered () {List names = Lists.newArrayList ("John", "Jane", "Adam", "Tom"); Výsledok zbierky = Collections2.filter (names, Predicates.or (Predicates.containsPattern ("J"), Predicates.not (Predicates.containsPattern ("a")))); assertEquals (3, result.size ()); assertThat (result, containsInAnyOrder ("John", "Jane", "Tom")); }

5. Počas filtrovania kolekcie odstráňte nulové hodnoty

Môžeme vyčistiť nulový hodnoty zo zbierky filtrovaním pomocou Predicates.notNull () ako v nasledujúcom príklade:

@Test public void whenRemoveNullFromCollection_thenRemoved () {List names = Lists.newArrayList ("John", null, "Jane", null, "Adam", "Tom"); Výsledok zbierky = Collections2.filter (names, Predicates.notNull ()); assertEquals (4, result.size ()); assertThat (result, containsInAnyOrder ("John", "Jane", "Adam", "Tom")); }

6. Skontrolujte, či sa všetky prvky v kolekcii zhodujú s podmienkou

Ďalej skontrolujeme, či všetky prvky v kolekcii zodpovedajú určitej podmienke. Použijeme Iterables.all () aby sme skontrolovali, či všetky mená obsahujú „n“ alebo „m“, potom skontrolujeme, či všetky prvky obsahujú „a“:

@Test public void whenCheckingIfAllElementsMatchACondition_thenCorrect () m ")); assertTrue (result); result = Iterables.all (names, Predicates.containsPattern (" a ")); assertFalse (result); 

7. Transformujte zbierku

Teraz - pozrime sa, ako na to transformovať kolekciu pomocou Guavy Funkcia. V nasledujúcom príklade - transformujeme a Zoznam mien do a Zoznam z Celé čísla (dĺžka mena) s Iterables.transform ():

@Test public void whenTransformWithIterables_thenTransformed () {Function function = new Function () {@Override public Integer apply (String input) {return input.length (); }}; Názvy zoznamu = Lists.newArrayList ("John", "Jane", "Adam", "Tom"); Iterable result = Iterables.transform (názvy, funkcia); assertThat (výsledok, obsahuje (4, 4, 4, 3)); }

Môžeme tiež použiť Collections2.transform () API ako v nasledujúcom príklade:

@ Test public void whenTransformWithCollections2_thenTransformed () {Function func = new Function () {@Override public Integer apply (String input) {return input.length (); }}; Názvy zoznamu = Lists.newArrayList ("John", "Jane", "Adam", "Tom"); Výsledok zbierky = Collections2.transform (names, func); assertEquals (4, result.size ()); assertThat (výsledok, obsahuje (4, 4, 4, 3)); výsledok.odstrániť (3); assertEquals (3, names.size ()); }

Všimnite si, že výstup Collections.transform () je živý pohľad na originál Zbierka- zmeny v jednej ovplyvňujú druhú.

A - rovnako ako predtým - ak sa pokúsime pridať do výstupu prvok Zbierka, an UnsupportedOperationException bude vyhodený.

8. Vytvorte Funkcia od Predikát

Môžeme aj tvoriť Funkcia od a Predikát použitím Functions.fromPredicate (). Toto bude samozrejme funkcia, ktorá transformuje vstupy na Boolovský, podľa stavu predikátu.

V nasledujúcom príklade transformujeme a Zoznam mien do zoznamu boolov, kde každý prvok predstavuje, ak názov obsahuje „m“:

@Test public void whenCreatingAFunctionFromAPredicate_thenCorrect () {List names = Lists.newArrayList ("John", "Jane", "Adam", "Tom"); Výsledok zbierky = Collections2.transform (names, Functions.forPredicate (Predicates.containsPattern ("m"))); assertEquals (4, result.size ()); assertThat (result, contains (false, false, true, true)); }

9. Zloženie dvoch funkcií

Ďalej - poďme sa pozrieť na to, ako transformovať zbierku pomocou zloženého Funkcia.

Functions.compose () vráti zloženie dvoch funkcií, keď použije druhú Funkcia na výstupe prvého Funkcia.

V nasledujúcom príklade - prvom Funkcia názov transformujte na jeho dĺžku, potom druhú Funkcia transformuje dĺžku na a boolovský hodnota, ktorá predstavuje, ak je dĺžka názvu párna:

@Test public void whenTransformingUsingComposedFunction_thenTransformed () {Function f1 = new Function () {@Override public Integer apply (String input) {return input.length (); }}; Funkcia f2 = new Function () {@Override public Boolean apply (Integer input) {return input% 2 == 0; }}; Názvy zoznamu = Lists.newArrayList ("John", "Jane", "Adam", "Tom"); Výsledok zbierky = Collections2.transform (names, Functions.compose (f2, f1)); assertEquals (4, result.size ()); assertThat (result, contains (true, true, true, false)); }

10. Kombinujte filtrovanie a transformáciu

A teraz - pozrime sa na ďalšie vynikajúce API, ktoré má Guava - také, ktoré nám skutočne umožní reťaziť filtrovanie a transformáciu dohromady - Plynulé.

V nasledujúcom príklade - filtrujeme Zoznam mien potom transformujte pomocou Plynulé:

@Test public void whenFilteringAndTransformingCollection_thenCorrect () {Predicate predicate = new Predicate () {@Override public boolean apply (String input)}; Funkcia func = new Function () {@Override public Integer apply (String input) {return input.length (); }}; Názvy zoznamu = Lists.newArrayList ("John", "Jane", "Adam", "Tom"); Výsledok zbierky = FluentIterable.from (names) .filter (predicate) .transform (func) .toList (); assertEquals (2, result.size ()); assertThat (result, containsInAnyOrder (4, 3)); }

Za zmienku stojí, že v niektorých prípadoch je imperatívna verzia čitateľnejšia a mala by sa uprednostniť pred funkčným prístupom.

11. Záver

Nakoniec sme sa naučili, ako filtrovať a transformovať zbierky pomocou Guavy. Použili sme Collections2.filter () a Iterables.filter () API na filtrovanie, ako aj Collections2.transform () a Iterables.transform () transformovať zbierky.

Nakoniec sme sa rýchlo pozreli na veľmi zaujímavé Plynulé plynulé API, ktoré kombinuje filtrovanie aj transformáciu.

Implementácia všetkých týchto príkladov a útržkov kódu nájdete v projekte GitHub - toto je projekt založený na Maven, takže by malo byť ľahké ho importovať a spustiť tak, ako je.


$config[zx-auto] not found$config[zx-overlay] not found