Java 8-predikatenketen

1. Overzicht

In deze korte tutorial, we bespreken verschillende manieren om te ketenen Predikaten in Java 8.

2. Basisvoorbeeld

Eerste, laten we eens kijken hoe we een simple Predikaat om een Lijst van namen:

@Test public void whenFilterList_thenSuccess () {List names = Arrays.asList ("Adam", "Alexander", "John", "Tom"); Lijstresultaat = names.stream () .filter (naam -> naam.startsWith ("A")) .collect (Collectors.toList ()); assertEquals (2, result.size ()); assertThat (resultaat, bevat ("Adam", "Alexander")); }

In dit voorbeeld hebben we onze Lijst van namen om alleen namen achter te laten die met een "A" beginnen met de Predikaat:

naam -> naam.startsWith ("A")

Maar wat als we er meerdere willen toepassen? Predikaten?

3. Meerdere filters

Als we er meerdere wilden toepassen Predikaten, een optie is om eenvoudig meerdere filters aan elkaar te koppelen:

@Test public void whenFilterListWithMultipleFilters_thenSuccess () {List result = names.stream () .filter (name -> name.startsWith ("A")) .filter (name -> name.length () <5) .collect (Collectors. toList ()); assertEquals (1, result.size ()); assertThat (resultaat, bevat ("Adam")); }

We hebben nu ons voorbeeld bijgewerkt om onze lijst te filteren door namen te extraheren die beginnen met "A" en een lengte hebben die kleiner is dan 5.

We hebben twee filters gebruikt - een voor elk Predikaat.

4. Complex Predikaat

Nu, in plaats van meerdere filters te gebruiken, we kunnen één filter gebruiken met een complex Predikaat:

@Test public void whenFilterListWithComplexPredicate_thenSuccess () {List result = names.stream () .filter (name -> name.startsWith ("A") && name.length () <5) .collect (Collectors.toList ()); assertEquals (1, result.size ()); assertThat (resultaat, bevat ("Adam")); }

Deze optie is flexibeler dan de eerste, zoals we kunnen bitsgewijze bewerkingen gebruiken om het Predikaatzo complex als we willen.

5. Combineren Predikaten

Vervolgens, als we geen complex willen bouwen Predikaat met behulp van bitsgewijze bewerkingen, Java 8 Predikaat heeft handige methoden die we kunnen gebruiken om te combineren Predikaten.

We zullen combineren Predikaten met behulp van de methoden Predicaat. En (), Predicaat. Of (), en Predicate.negate ().

5.1. Predicaat. En ()

In dit voorbeeld definiëren we onze Predikaten expliciet, en dan combineren we ze met Predicaat. En ():

@Test public void whenFilterListWithCombinedPredicatesUsingAnd_thenSuccess () {Predicate predicate1 = str -> str.startsWith ("A"); Predikaat predikaat2 = str -> str.length () <5; Lijstresultaat = names.stream () .filter (predikaat1.en (predikaat2)) .collect (Collectors.toList ()); assertEquals (1, result.size ()); assertThat (resultaat, bevat ("Adam")); }

Zoals we kunnen zien, is de syntaxis redelijk intuïtief en suggereren de namen van de methoden het type bewerking. Gebruik makend van en(), we hebben onze gefilterd Lijst door alleen namen te extraheren die aan beide voorwaarden voldoen.

5.2. Predicaat. Of ()

We kunnen ook gebruik maken van Predicaat. Of () combineren Predikaten.

Laten we namen extraheren die beginnen met "J", evenals namen met een lengte van minder dan 4:

@Test openbare leegte whenFilterListWithCombinedPredicatesUsingOr_thenSuccess () {Predicaat predicaat1 = str -> str.startsWith ("J"); Predikaat predikaat2 = str -> str.length () <4; Lijstresultaat = names.stream () .filter (predicate1.or (predicate2)) .collect (Collectors.toList ()); assertEquals (2, result.size ()); assertThat (resultaat, bevat ("John", "Tom")); }

5.3. Predicate.negate ()

We kunnen gebruiken Predicate.negate () bij het combineren van onze Predikaten ook:

@Test openbare ongeldigheid whenFilterListWithCombinedPredicatesUsingOrAndNegate_thenSuccess () {Predicaat predicaat1 = str -> str.startsWith ("J"); Predikaat predikaat2 = str -> str.length () <4; Lijstresultaat = names.stream () .filter (predicate1.or (predicate2.negate ())) .collect (Collectors.toList ()); assertEquals (3, result.size ()); assertThat (resultaat, bevat ("Adam", "Alexander", "John")); }

Hier hebben we een combinatie van gebruikt of() en ontkennen om het Lijst door namen die beginnen met "J" of een lengte hebben die niet minder is dan 4.

5.4. Combineren Predikaten In lijn

We hoeven ons niet expliciet te definiëren Predikaten gebruiken en(),of(), en ontkennen ().

We kunnen ze ook inline gebruiken door de Predikaat:

@Test public void whenFilterListWithCombinedPredicatesInline_thenSuccess () {List result = names.stream () .filter (((Predicaat) naam -> naam.startsWith ("A")) .en (naam -> naam.length () <5)) .collect (Collectors.toList ()); assertEquals (1, result.size ()); assertThat (resultaat, bevat ("Adam")); }

6. Combineren van een verzameling van Predikaten

Tenslotte, laten we eens kijken hoe we een verzameling van Predikaten door ze te verminderen.

In het volgende voorbeeld hebben we een Lijst van Predikaten die we hebben gecombineerd met Predicaat. En ():

@Test openbare leegte whenFilterListWithCollectionOfPredicatesUsingAnd_thenSuccess () {Lijst allPredicates = nieuwe ArrayList(); allPredicates.add (str -> str.startsWith ("A")); allPredicates.add (str -> str.contains ("d")); allPredicates.add (str -> str.length ()> 4); Lijstresultaat = names.stream () .filter (allPredicates.stream (). Reduc (x-> true, Predicaat :: en)) .collect (Collectors.toList ()); assertEquals (1, result.size ()); assertThat (resultaat, bevat ("Alexander")); }

Merk op dat we onze basisidentiteit gebruiken als:

x-> waar

Maar dat zal anders zijn als we ze met elkaar willen combineren Predicaat. Of ():

@Test public void whenFilterListWithCollectionOfPredicatesUsingOr_thenSuccess () {List result = names.stream () .filter (allPredicates.stream (). Reduc (x-> false, Predicate :: or)) .collect (Collectors.toList ()); assertEquals (2, result.size ()); assertThat (resultaat, bevat ("Adam", "Alexander")); }

7. Conclusie

In dit artikel hebben we verschillende manieren onderzocht om predicaten in Java 8 te koppelen, met behulp van filter(), gebouwencomplex Predikaten, en combineren Predikaten.

De volledige broncode is beschikbaar op GitHub.