Einführung in Java 8 Streams

Einführung in Java 8 Streams

1. Überblick

In diesem Artikel werfen wir einen kurzen Blick auf eine der wichtigsten neuen Funktionen, die Java 8 hinzugefügt hat - Streams.

Wir erklären, worum es bei Streams geht, und zeigen anhand einfacher Beispiele die Erstellung und die grundlegenden Stream-Vorgänge.

2. Stream-API

Eine der wichtigsten neuen Funktionen in Java 8 ist die Einführung der Stream-Funktionalitätjava.util.stream, die Klassen zum Verarbeiten von Elementsequenzen enthält.

Die zentrale API-Klasse istStream<T>.. Der folgende Abschnitt zeigt, wie Streams mit den vorhandenen Datenproviderquellen erstellt werden können.

2.1. Stream-Erstellung

Streams können aus verschiedenen Elementquellen erstellt werden, z. Sammlung oder Array mit Hilfe der Methodenstream() undof():

String[] arr = new String[]{"a", "b", "c"};
Stream stream = Arrays.stream(arr);
stream = Stream.of("a", "b", "c");

Die Standardmethode vonstream()wird zur Schnittstelle vonCollectionhinzugefügt und ermöglicht das Erstellen vonStream<T> unter Verwendung einer beliebigen Sammlung als Elementquelle:

Stream stream = list.stream();

2.2. Multithreading mit Streams

Die Stream-API vereinfacht auch das Multithreading, indem dieparallelStream()-Methode bereitgestellt wird, mit der Operationen über die Elemente des Streams im parallelen Modus ausgeführt werden.

Mit dem folgenden Code können Sie die MethodedoWork() für jedes Element des Streams parallel ausführen:

list.parallelStream().forEach(element -> doWork(element));

Im folgenden Abschnitt werden einige grundlegende Stream-API-Vorgänge vorgestellt.

3. Stream-Operationen

Es gibt viele nützliche Vorgänge, die für einen Stream ausgeführt werden können.

Sie sind inintermediate operations (RückgabeStream<T>) undterminal operations (Rückgabe eines Ergebnisses eines bestimmten Typs) unterteilt. Zwischenoperationen ermöglichen das Verketten.

Es ist auch erwähnenswert, dass Vorgänge in Streams die Quelle nicht ändern.

Hier ein kurzes Beispiel:

long count = list.stream().distinct().count();

Diedistinct()-Methode stellt also eine Zwischenoperation dar, die einen neuen Stream eindeutiger Elemente des vorherigen Streams erstellt. Die Methodecount() ist eine Terminaloperation,, die die Größe des Streams zurückgibt.

3.1. Iterieren

Die Stream-API hilft dabei,for, for-each- undwhile-Schleifen zu ersetzen. Es ermöglicht die Konzentration auf die Logik der Operation, jedoch nicht auf die Iteration über die Folge von Elementen. Zum Beispiel:

for (String string : list) {
    if (string.contains("a")) {
        return true;
    }
}

Dieser Code kann mit nur einer Zeile Java 8-Code geändert werden:

boolean isExist = list.stream().anyMatch(element -> element.contains("a"));

3.2. Filtern

Diefilter()-Methode ermöglicht es uns, einen Strom von Elementen auszuwählen, die ein Prädikat erfüllen.

Betrachten Sie beispielsweise die folgende Liste:

ArrayList list = new ArrayList<>();
list.add("One");
list.add("OneAndOnly");
list.add("Derek");
list.add("Change");
list.add("factory");
list.add("justBefore");
list.add("Italy");
list.add("Italy");
list.add("Thursday");
list.add("");
list.add("");

Der folgende Code erstelltStream<String> vonList<String>, findet alle Elemente dieses Streams, diechar “d” enthalten, und erstellt einen neuen Stream, der nur die gefilterten Elemente enthält:

Stream stream = list.stream().filter(element -> element.contains("d"));

3.3. Kartierung

Um Elemente vonStream durch Anwenden einer speziellen Funktion auf sie zu konvertieren und diese neuen Elemente inStream zu sammeln, können wir die Methodemap() verwenden:

List uris = new ArrayList<>();
uris.add("C:\\My.txt");
Stream stream = uris.stream().map(uri -> Paths.get(uri));

Der obige Code konvertiert alsoStream<String> inStream<Path>, indem auf jedes Element der anfänglichenStream ein spezifischer Lambda-Ausdruck angewendet wird.

Wenn Sie einen Stream haben, in dem jedes Element eine eigene Folge von Elementen enthält, und Sie einen Stream dieser inneren Elemente erstellen möchten, sollten Sie die MethodeflatMap()verwenden:

List details = new ArrayList<>();
details.add(new Detail());
Stream stream
  = details.stream().flatMap(detail -> detail.getParts().stream());

In diesem Beispiel haben wir eine Liste von Elementen vom TypDetail.. Die KlasseDetail enthält ein FeldPARTS,, das mit Hilfe vonflatMap() einList<String>. ist Methode Jedes Element aus FeldPARTS wird extrahiert und dem neuen resultierenden Stream hinzugefügt. Danach gehen die anfänglichenStream<Detail>. verloren

3.4. Passend

Stream API bietet eine praktische Reihe von Instrumenten, um Elemente einer Sequenz anhand eines Prädikats zu validieren. Dazu kann eine der folgenden Methoden verwendet werden:anyMatch(), allMatch(), noneMatch(). Ihre Namen sind selbsterklärend. Dies sind Terminaloperationen, die einen Booleschen Wert zurückgeben.

boolean isValid = list.stream().anyMatch(element -> element.contains("h")); // true
boolean isValidOne = list.stream().allMatch(element -> element.contains("h")); // false
boolean isValidTwo = list.stream().noneMatch(element -> element.contains("h")); // false

3.5. Die Ermäßigung

Mit der Stream-API kann eine Folge von Elementen mithilfe derreduce()-Methode vom TypStream gemäß einer bestimmten Funktion auf einen bestimmten Wert reduziert werden. Diese Methode verwendet zwei Parameter: Erstens - Startwert, zweitens - Akkumulatorfunktion.

Stellen Sie sich vor, Sie habenList<Integer> und möchten eine Summe aller dieser Elemente und einige anfänglicheInteger (in diesem Beispiel 23). Sie können also den folgenden Code ausführen und das Ergebnis ist 26 (23 + 1 + 1 + 1).

List integers = Arrays.asList(1, 1, 1);
Integer reduced = integers.stream().reduce(23, (a, b) -> a + b);

3.6. Sammeln

Die Reduzierung kann auch durch die Methodecollect() vom TypStream. erfolgen. Diese Operation ist sehr praktisch, wenn ein Stream inCollection oderMap konvertiert und ein Stream dargestellt wird in Form einer einzelnen Zeichenfolge. Es gibt eine GebrauchsklasseCollectors, die eine Lösung für fast alle typischen Erfassungsvorgänge bietet. Für einige nicht triviale Aufgaben können benutzerdefinierteCollector erstellt werden.

List resultList
  = list.stream().map(element -> element.toUpperCase()).collect(Collectors.toList());

Dieser Code verwendet die Operation des Terminalscollect(), umStream<String> aufList<String>. zu reduzieren

4. Schlussfolgerungen

In diesem Artikel haben wir kurz auf Java-Streams eingegangen - definitiv eine der interessantesten Java 8-Funktionen.

Es gibt viel fortgeschrittenere Beispiele für die Verwendung von Streams. Ziel dieses Aufsatzes war es lediglich, eine schnelle und praktische Einführung in die Funktionsweise zu geben und als Ausgangspunkt für das Erkunden und Weiterlernen zu dienen.

Der dem Artikel beiliegende Quellcode istover on GitHub. verfügbar