Ich höre oft "Ich habe versucht, mit Java8 zu streamen, aber ich bin nicht daran gewöhnt" oder "Ich kann es nicht tun, wenn ich versuche, etwas Schwieriges zu tun", also fasse ich es zusammen.
Wenn Sie den Typ kennen, scheinen Sie 80% zu kennen. Machen wir also ein Bild daraus.
~~ Der Artikel ist übrigens lang, aber es reicht aus, die erste Überschrift "[Hauptgeschichte-") zu lesen! ~~
Es ist zu lang, um ruhig zu denken, also habe ich es geteilt.
Lassen Sie uns die drei grundlegenden Hände gedrückt halten.
Sie sind vielleicht nicht mit "Reduzieren" vertraut, aber es ist ein von Google empfohlenes "MapReduce" -Modell, daher wird es mit "Karte" besprochen. -> wiki
Schauen wir uns das folgende Beispiel an.
/*
*Es gibt das folgende Protokoll
*Etikett oder Etikett:Ausgabe zeilenweise im Millisekundenformat
*
*Finden Sie die Summe von Millisekunden
*/
List<String> lines = Arrays.asList(
"application-boot", "access-dispatch:10", "dispatched", "authentication:30", "database-access:45", "response-creation:15", "access-logging"
);
Das Wichtigste ist der Typ. Haben Sie also keine Angst vor Generika und überprüfen Sie ihn einfach.
Dann werden viele solcher Bilder herauskommen.
A-> B f
wird im Java-Code alsB f (a);
geschrieben, und A
und B
sind String
undOptional <Integer>. Enthält einen bestimmten Typ wie
. Mit anderen Worten, Generika.
filter Die Definition von "Filter" ist wie folgt.
Stream<T> filter(Predicate<? super T> predicate);
Vergessen Sie "Prädikat
Nehmen wir die Typennotation von "Prädikat
Stream<T> filter((T -> bool) f);
Um "Filter" zu verwenden, um "Zeilen" nur mit ":" zu erstellen, können Sie schreiben:
lines.stream()
.filter(line -> line.contains(":")) // ["access-dispatch:10", "authentication:30", "database-access:45", "response-creation:15"]
Wenn Sie die Definition als "T-> bool" schreiben, sieht die Implementierung "line-> line.contains (": ")" gleich aus. (In diesem Thema ist "T" speziell "String")
Ist es so, wenn es auf einem Bild gezeichnet wird?
filter
bedeutet, dass sich der ** Typ ** nicht ändert, aber die ** Nummer ** ändert.
map Die Definition von "Karte" ist wie folgt.
<R> Stream<R> map(Function<? super T, ? extends R> mapper);
In gleicher Weise wird dies auch vereinfacht.
Stream<R> map((T -> R) f);
Verwenden von map
, um die Zeile von label zu erstellen: millisec`` Integer
kann wie folgt nach filter
geschrieben werden.
lines.stream()
.filter(line -> line.contains(":")) // ["access-dispatch:10", "authentication:30", "database-access:45", "response-creation:15"]
.map(line -> Integer.valueOf(line.split(":")[1])) // [10, 30, 45, 15]
Auch hier hat die Implementierung die gleiche Form wie die Definition T-> R
.
(In diesem Thema ist R
speziell Integer
, daher wäre es schön, wenn T-> R
wie String-> Integer
aussieht.)
Ist es so, wenn es auf einem Bild gezeichnet wird?
map
bedeutet, dass sich die ** Nummer ** nicht ändert, aber der ** Typ ** ändert.
reduce Es gibt drei Definitionen von "Reduzieren" im Java8-Stream, aber das werde ich jetzt verwenden.
T reduce(T identity, BinaryOperator<T> accumulator);
BinaryOperator <T>
ist ein wenig unbekannt, aber es bedeutet "zwei Argumente sind T
und der Rückgabewert ist T
".
Vereinfachen wir dies, ohne Angst zu haben.
T reduce(T t, ((T, T) -> T) f);
"Reduzieren" wird im Allgemeinen als "Faltung" bezeichnet und ist ein Prozess, bei dem Ergebnisse in der Reihenfolge ganz oben auf der Liste gesammelt werden.
Um mit "Reduzieren" eine Zeile aus "Ganzzahl" zur Summe von "Ganzzahl" zu machen, können Sie diese nach "Karte" schreiben.
lines.stream()
.filter(line -> line.contains(":")) // ["access-dispatch:10", "authentication:30", "database-access:45", "response-creation:15"]
.map(line -> Integer.valueOf(line.split(":")[1])) // [10, 30, 45, 15]
.reduce(0, (acc, n) -> acc + n) // 100
Die Definition enthält einige Klammern, die jedoch etwas einfacher zu verstehen sein sollten, da T, (T, T) -> T
und 0, (acc, n) -> ...
dieselbe Form haben.
Ist es so, wenn es auf einem Bild gezeichnet wird?
redu
ist ein Prozess, bei dem ** Listenelemente ** zu ** Einzelergebnissen ** werden.
Das ist klar!
*Finden Sie die Summe von Millisekunden
Ist
// (Erneut veröffentlichen)
lines.stream()
.filter(line -> line.contains(":")) // ["access-dispatch:10", "authentication:30", "database-access:45", "response-creation:15"]
.map(line -> Integer.valueOf(line.split(":")[1])) // [10, 30, 45, 15]
.reduce(0, (acc, n) -> acc + n) // 100
Ich habe es mit gelöst.
Vorerst werde ich das ganze Bild posten.
Alle Extras von hier an wurden in die folgenden Artikel unterteilt.
Listenverarbeitung unter Bildern verstanden --java8 stream / javaslang --bonus
Erfrischend.
Recommended Posts