├── .gitignore ├── AllesImFluss.pdf ├── AllesImFluss2.pdf ├── Java_Screams-_Oh_you_mean_Java_Streams.pdf ├── Readme.md ├── pom.xml ├── rhyme.txt └── src ├── main ├── java │ └── net │ │ └── mirwaldt │ │ └── streams │ │ ├── Example_01_ForeachWrite.java │ │ ├── Example_02_StatefulPredicate.java │ │ ├── Example_03_Top10.java │ │ ├── Example_03a_Top10.java │ │ ├── Example_03b_Top10.java │ │ ├── Example_04_FilterMapGroupingBy.java │ │ ├── Example_05_CamelCase.java │ │ ├── Example_06_allMatch.java │ │ ├── Example_07_MergeMapsByMin.java │ │ ├── Example_08_PrintOutNamesInUpperCase.java │ │ ├── Example_09_First100Primes.java │ │ ├── Example_10_MapMulti.java │ │ ├── Example_11_BadForeach.java │ │ ├── Example_12_EmptyStream.java │ │ ├── Example_13_Iterator.java │ │ ├── Example_14_TransposeMatrix.java │ │ ├── Example_15_Fibonacci.java │ │ ├── Example_16_HandlingCheckedExceptions.java │ │ └── Example_17_DebuggingWithPeek.java └── resources │ └── German.txt └── test └── java └── net └── mirwaldt └── streams └── Example_14_Fibonacci_Test.java /.gitignore: -------------------------------------------------------------------------------- 1 | # from https://gist.github.com/dedunumax/54e82214715e35439227#file-gitignore-java 2 | ############################## 3 | ## Java 4 | ############################## 5 | .mtj.tmp/ 6 | *.class 7 | *.jar 8 | *.war 9 | *.ear 10 | *.nar 11 | hs_err_pid* 12 | 13 | ############################## 14 | ## Maven 15 | ############################## 16 | target/ 17 | pom.xml.tag 18 | pom.xml.releaseBackup 19 | pom.xml.versionsBackup 20 | pom.xml.next 21 | pom.xml.bak 22 | release.properties 23 | dependency-reduced-pom.xml 24 | buildNumber.properties 25 | .mvn/timing.properties 26 | .mvn/wrapper/maven-wrapper.jar 27 | 28 | ############################## 29 | ## Gradle 30 | ############################## 31 | bin/ 32 | build/ 33 | .gradle 34 | .gradletasknamecache 35 | gradle-app.setting 36 | !gradle-wrapper.jar 37 | 38 | ############################## 39 | ## IntelliJ 40 | ############################## 41 | out/ 42 | .idea/ 43 | .idea_modules/ 44 | *.iml 45 | *.ipr 46 | *.iws 47 | 48 | ############################## 49 | ## Eclipse 50 | ############################## 51 | .settings/ 52 | bin/ 53 | tmp/ 54 | .metadata 55 | .classpath 56 | .project 57 | *.tmp 58 | *.bak 59 | *.swp 60 | *~.nib 61 | local.properties 62 | .loadpath 63 | .factorypath 64 | 65 | ############################## 66 | ## NetBeans 67 | ############################## 68 | nbproject/private/ 69 | build/ 70 | nbbuild/ 71 | dist/ 72 | nbdist/ 73 | nbactions.xml 74 | nb-configuration.xml 75 | 76 | ############################## 77 | ## Visual Studio Code 78 | ############################## 79 | .vscode/ 80 | .code-workspace 81 | 82 | ############################## 83 | ## OS X 84 | ############################## 85 | .DS_Store 86 | -------------------------------------------------------------------------------- /AllesImFluss.pdf: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mmirwaldt/JavaStreamsForTheAdvanced/b72a0d67364d6824c503168516ae1f88b0a4fa33/AllesImFluss.pdf -------------------------------------------------------------------------------- /AllesImFluss2.pdf: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mmirwaldt/JavaStreamsForTheAdvanced/b72a0d67364d6824c503168516ae1f88b0a4fa33/AllesImFluss2.pdf -------------------------------------------------------------------------------- /Java_Screams-_Oh_you_mean_Java_Streams.pdf: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/mmirwaldt/JavaStreamsForTheAdvanced/b72a0d67364d6824c503168516ae1f88b0a4fa33/Java_Screams-_Oh_you_mean_Java_Streams.pdf -------------------------------------------------------------------------------- /Readme.md: -------------------------------------------------------------------------------- 1 | # Java Streams for the advanced 2 | 3 | ### What is this? 4 | 5 | This project includes the slides and the code examples of the presentations "Alles im Fluss - Java Streams für Fortgeschrittene" (German) and "Java Screams? Oh, you mean Java Streams! Java Streams for the advanced". 6 | 7 | ### Who owns the copyright for this project? 8 | 9 | Michael Mirwaldt owns the copyright (c) for this project since 2022. All rights reserved to him. 10 | 11 | ### How is this project licensed? 12 | 13 | Creative Commons License
14 | This work is licensed under a Creative Commons 15 | Attribution-NonCommercial-NoDerivatives 4.0 International License. 16 | -------------------------------------------------------------------------------- /pom.xml: -------------------------------------------------------------------------------- 1 | 2 | 5 | 4.0.0 6 | 7 | net.mirwaldt 8 | JavaStreamsForTheAdvanced 9 | 1.0.0-SNAPSHOT 10 | 11 | 12 | 16 13 | 16 14 | 15 | 16 | 17 | 18 | org.junit.platform 19 | junit-platform-launcher 20 | 1.8.0-M1 21 | test 22 | 23 | 24 | org.junit.jupiter 25 | junit-jupiter-engine 26 | 5.8.0-M1 27 | test 28 | 29 | 30 | org.junit.jupiter 31 | junit-jupiter-params 32 | 5.8.0-M1 33 | test 34 | 35 | 36 | org.ow2.asm 37 | asm 38 | 9.1 39 | 40 | 41 | org.ow2.asm 42 | asm-commons 43 | 9.1 44 | 45 | 46 | -------------------------------------------------------------------------------- /rhyme.txt: -------------------------------------------------------------------------------- 1 | There was an old lady who swallowed a fly. 2 | I dunno why she swallowed that fly, 3 | Perhaps she will die. 4 | 5 | There was an old lady who swallowed a spider, 6 | That wiggled and wiggled and tickled inside her. 7 | She swallowed the spider to catch the fly. 8 | But I dunno why she swallowed that fly - 9 | Perhaps she will die. 10 | 11 | There was an old lady who swallowed a bird; 12 | How absurd, to swallow a bird! 13 | She swallowed the bird to catch the spider 14 | That wiggled and wiggled and tickled inside her. 15 | She swallowed the spider to catch the fly. 16 | But I dunno why she swallowed that fly - 17 | Perhaps she will die. 18 | 19 | There was an old lady who swallowed a cat. 20 | Imagine that, she swallowed a cat. 21 | She swallowed the cat to catch the bird ... 22 | She swallowed the bird to catch the spider 23 | That wiggled and wiggled and tickled inside her . 24 | She swallowed the spider to catch the fly. 25 | But I dunno why she swallowed that fly 26 | Perhaps she will die. 27 | 28 | There was an old lady who swallowed a dog . 29 | What a hog ! To swallow a dog ! 30 | She swallowed the dog to catch the cat ... 31 | She swallowed the cat to catch the bird ... 32 | She swallowed the bird to catch the spider 33 | That wiggled and wiggled and tickled inside her . 34 | She swallowed the spider to catch the fly . 35 | But I dunno why she swallowed that fly 36 | Perhaps she will die. 37 | 38 | There was an old lady who swallowed a goat . 39 | Just opened her throat and swallowed a goat ! 40 | She swallowed the goat to catch the dog ... 41 | She swallowed the dog to catch the cat . 42 | She swallowed the cat to catch the bird ... 43 | She swallowed the bird to catch the spider 44 | That wiggled and wiggled and tickled inside her . 45 | She swallowed the spider to catch the fly . 46 | But I dunno why she swallowed that fly 47 | Perhaps she will die. 48 | 49 | There was an old lady who swallowed a cow. 50 | I do not know how she swallowed a cow! 51 | She swallowed the cow to catch the goat ... 52 | She swallowed the goat to catch the dog ... 53 | She swallowed the dog to catch the cat ... 54 | She swallowed the cat to catch the bird ... 55 | She swallowed the bird to catch the spider 56 | That wiggled and wiggled and tickled inside her. 57 | She swallowed the spider to catch the fly. 58 | But I dunno why she swallowed that fly 59 | Perhaps she will die. 60 | 61 | There was an old lady who swallowed a horse - 62 | She is dead, of course. -------------------------------------------------------------------------------- /src/main/java/net/mirwaldt/streams/Example_01_ForeachWrite.java: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright (c) 2022, Michael Mirwaldt. All rights reserved. 3 | * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. 4 | * 5 | * Creative Commons License 6 | *
This work is licensed under a 7 | * Creative Commons Attribution-NonCommercial-NoDerivatives 4.0 International License. 8 | */ 9 | 10 | package net.mirwaldt.streams; 11 | 12 | import java.util.ArrayList; 13 | import java.util.List; 14 | import java.util.Set; 15 | 16 | public class Example_01_ForeachWrite { 17 | public static void main(String[] args) { 18 | Set acceptable = Set.of(1, 2, 3, 5, 6, 7, 9, 11); 19 | Set inputs = Set.of(0, 2, 3, 4, 8, 9); 20 | 21 | List flawed = new ArrayList<>(); 22 | inputs.stream() 23 | .filter(acceptable::contains) // OK 24 | .forEach(flawed::add); // NO! 25 | System.out.println(flawed); 26 | 27 | List better = inputs.stream() 28 | .filter(acceptable::contains) 29 | .toList(); 30 | System.out.println(better); 31 | } 32 | } 33 | -------------------------------------------------------------------------------- /src/main/java/net/mirwaldt/streams/Example_02_StatefulPredicate.java: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright (c) 2022, Michael Mirwaldt. All rights reserved. 3 | * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. 4 | * 5 | * Creative Commons License 6 | *
This work is licensed under a 7 | * Creative Commons Attribution-NonCommercial-NoDerivatives 4.0 International License. 8 | */ 9 | 10 | package net.mirwaldt.streams; 11 | 12 | import java.util.List; 13 | import java.util.function.Predicate; 14 | import java.util.stream.Collectors; 15 | 16 | public class Example_02_StatefulPredicate { 17 | public static void main(String[] args) { 18 | List lineNumbers = List.of(1, 2, 3, 5, 6, 8, 9); 19 | List flawedThirds = lineNumbers.stream() 20 | .filter(new Predicate<>() { 21 | int counter = 1; 22 | 23 | public boolean test(Integer value) { 24 | return counter++ % 3 == 0; 25 | } 26 | }) 27 | .toList(); 28 | System.out.println(flawedThirds); 29 | 30 | List betterThirds = lineNumbers.stream() 31 | .filter(elem -> (lineNumbers.indexOf(elem) + 1) % 3 == 0) 32 | .collect(Collectors.toList()); 33 | System.out.println(betterThirds); 34 | } 35 | } 36 | -------------------------------------------------------------------------------- /src/main/java/net/mirwaldt/streams/Example_03_Top10.java: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright (c) 2022, Michael Mirwaldt. All rights reserved. 3 | * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. 4 | * 5 | * Creative Commons License 6 | *
This work is licensed under a 7 | * Creative Commons Attribution-NonCommercial-NoDerivatives 4.0 International License. 8 | */ 9 | 10 | package net.mirwaldt.streams; 11 | 12 | import java.io.IOException; 13 | import java.nio.file.Files; 14 | import java.nio.file.Path; 15 | import java.util.*; 16 | 17 | import static java.lang.String.CASE_INSENSITIVE_ORDER; 18 | import static java.util.Collections.reverseOrder; 19 | import static java.util.stream.Collectors.*; 20 | 21 | public class Example_03_Top10 { 22 | public static void main(String[] args) throws IOException { 23 | // with one stream 24 | List lines = Files.readAllLines(Path.of("rhyme.txt")); 25 | SortedMap> top10byOneStream = lines.stream() 26 | .filter(line -> !line.isEmpty()) 27 | .map(line -> line.replaceAll("[\\!|\\.|\\-|\\,|\\;]", "")) 28 | .flatMap(line -> Arrays.stream(line.split("\\s+"))) 29 | .collect(groupingBy(s -> s, () -> new TreeMap<>(CASE_INSENSITIVE_ORDER), counting())) 30 | .entrySet().stream() 31 | .sorted((left, right) -> -Long.compare(left.getValue(), right.getValue())) 32 | .limit(10) 33 | .collect(groupingBy(Map.Entry::getValue, () -> new TreeMap<>(reverseOrder()), 34 | mapping(Map.Entry::getKey, toList()))); 35 | System.out.println("top10byOneStream=" + top10byOneStream); 36 | System.out.println(); 37 | 38 | // with several streams 39 | Map frequenciesByWord = lines.stream() 40 | .filter(line -> !line.isEmpty()) 41 | .map(line -> line.replaceAll("[\\!|\\.|\\-|\\,|\\;]", "")) 42 | .flatMap(line -> Arrays.stream(line.split("\\s+"))) 43 | .collect(groupingBy(s -> s, () -> new TreeMap<>(CASE_INSENSITIVE_ORDER), counting())); 44 | System.out.println("frequenciesByWord=" + frequenciesByWord); 45 | System.out.println(); 46 | 47 | SortedMap> wordsByFrequency = 48 | frequenciesByWord.entrySet() 49 | .stream() 50 | .collect(groupingBy(Map.Entry::getValue, () -> new TreeMap<>(reverseOrder()), 51 | mapping(Map.Entry::getKey, toList()))); 52 | System.out.println("wordsByFrequency=" + wordsByFrequency); 53 | System.out.println(); 54 | 55 | SortedMap> top10byMaps = 56 | wordsByFrequency.entrySet().stream() 57 | .flatMap(entry -> entry.getValue().stream().map(value -> Map.of(entry.getKey(), value))) 58 | .flatMap(map -> map.entrySet().stream()) 59 | .limit(10) 60 | .collect(groupingBy(Map.Entry::getKey, () -> new TreeMap<>(reverseOrder()), 61 | mapping(Map.Entry::getValue, toList()))); 62 | System.out.println("top10byMaps=" + top10byMaps); 63 | System.out.println(); 64 | 65 | // with several streams and a record 66 | record WordEntry(long frequency, String word) { 67 | } 68 | 69 | SortedMap> top10byRecord = wordsByFrequency.entrySet().stream() 70 | .flatMap(entry -> entry.getValue().stream() 71 | .map(value -> new WordEntry(entry.getKey(), value))) 72 | .limit(10) 73 | .collect(groupingBy(WordEntry::frequency, 74 | () -> new TreeMap<>(reverseOrder()), 75 | mapping(WordEntry::word, toList()))); 76 | System.out.println("top10byRecord=" + top10byRecord); 77 | } 78 | } 79 | -------------------------------------------------------------------------------- /src/main/java/net/mirwaldt/streams/Example_03a_Top10.java: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright (c) 2022, Michael Mirwaldt. All rights reserved. 3 | * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. 4 | * 5 | * Creative Commons License 6 | *
This work is licensed under a 7 | * Creative Commons Attribution-NonCommercial-NoDerivatives 4.0 International License. 8 | */ 9 | 10 | package net.mirwaldt.streams; 11 | 12 | import java.io.IOException; 13 | import java.nio.file.Files; 14 | import java.nio.file.Path; 15 | import java.util.*; 16 | 17 | import static java.lang.String.CASE_INSENSITIVE_ORDER; 18 | import static java.util.Collections.emptyMap; 19 | import static java.util.Collections.reverseOrder; 20 | import static java.util.stream.Collectors.*; 21 | 22 | /* 23 | This variation of Example_03_Top10 does not just take the first elements of the last word list and ignores the rest 24 | but includes all elements. This might lead to a top 10 with 11 elements because the 10th and 11th element have both 25 | the same frequency. 26 | E.g. 27 | ... 28 | top10={42=[the], 39=[swallowed], 38=[she], 23=[to], 21=[catch], 14=[a, fly, that], 13=[and], 12=[spider, wiggled]} 29 | top09={42=[the], 39=[swallowed], 38=[she], 23=[to], 21=[catch], 14=[a, fly, that], 13=[and]} 30 | top08={42=[the], 39=[swallowed], 38=[she], 23=[to], 21=[catch], 14=[a, fly, that]} 31 | top07={42=[the], 39=[swallowed], 38=[she], 23=[to], 21=[catch], 14=[a, fly, that]} 32 | top06={42=[the], 39=[swallowed], 38=[she], 23=[to], 21=[catch], 14=[a, fly, that]} 33 | top05={42=[the], 39=[swallowed], 38=[she], 23=[to], 21=[catch]} 34 | ... 35 | 36 | This was my first (flawed) attempt to find a solution. 37 | */ 38 | public class Example_03a_Top10 { 39 | public static void main(String[] args) throws IOException { 40 | // with one stream 41 | List lines = Files.readAllLines(Path.of("rhyme.txt")); 42 | SortedMap> top10Plus = lines.stream() 43 | .filter(line -> !line.isEmpty()) 44 | .map(line -> line.replaceAll("[\\!|\\.|\\-|\\,|\\;]", "")) 45 | .flatMap(line -> Arrays.stream(line.split("\\s+"))) 46 | .collect(groupingBy(s -> s, () -> new TreeMap<>(CASE_INSENSITIVE_ORDER), counting())) 47 | .entrySet().stream() 48 | .collect(groupingBy(Map.Entry::getValue, () -> new TreeMap<>(reverseOrder()), 49 | mapping(Map.Entry::getKey, toList()))) 50 | .entrySet().stream() 51 | .map(entry -> Map.of(entry.getKey(), entry.getValue())) 52 | .collect(() -> new TreeMap<>(reverseOrder()), 53 | (result, map) -> result.putAll((10 <= sumSizesOfValues(result)) ? emptyMap() : map), 54 | TreeMap::putAll); 55 | System.out.println("top10=" + top10Plus); 56 | System.out.println(); 57 | 58 | // with several streams 59 | Map frequenciesByWord = lines.stream() 60 | .filter(line -> !line.isEmpty()) 61 | .map(line -> line.replaceAll("[\\!|\\.|\\-|\\,|\\;]", "")) 62 | .flatMap(line -> Arrays.stream(line.split("\\s+"))) 63 | .collect(groupingBy(s -> s, () -> new TreeMap<>(CASE_INSENSITIVE_ORDER), counting())); 64 | System.out.println("frequenciesByWord=" + frequenciesByWord); 65 | System.out.println(); 66 | 67 | SortedMap> wordsByFrequency = 68 | frequenciesByWord.entrySet() 69 | .stream() 70 | .collect(groupingBy(Map.Entry::getValue, () -> new TreeMap<>(reverseOrder()), 71 | mapping(Map.Entry::getKey, toList()))); 72 | System.out.println("wordsByFrequency=" + wordsByFrequency); 73 | System.out.println(); 74 | 75 | SortedMap> onlyTop10Plus = 76 | wordsByFrequency.entrySet().stream() 77 | .map(entry -> Map.of(entry.getKey(), entry.getValue())) 78 | .collect(() -> new TreeMap<>(reverseOrder()), 79 | (result, map) -> result.putAll((10 <= sumSizesOfValues(result)) ? emptyMap() : map), 80 | TreeMap::putAll); 81 | System.out.println("onlyTop10=" + onlyTop10Plus); 82 | System.out.println(); 83 | } 84 | 85 | public static long sumSizesOfValues(SortedMap> map) { 86 | return map.values().stream().mapToLong(List::size).sum(); 87 | } 88 | } 89 | -------------------------------------------------------------------------------- /src/main/java/net/mirwaldt/streams/Example_03b_Top10.java: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright (c) 2022, Michael Mirwaldt. All rights reserved. 3 | * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. 4 | * 5 | * Creative Commons License 6 | *
This work is licensed under a 7 | * Creative Commons Attribution-NonCommercial-NoDerivatives 4.0 International License. 8 | */ 9 | 10 | package net.mirwaldt.streams; 11 | 12 | import java.io.IOException; 13 | import java.nio.file.Files; 14 | import java.nio.file.Path; 15 | import java.util.*; 16 | 17 | import static java.lang.String.CASE_INSENSITIVE_ORDER; 18 | import static java.util.Collections.emptyMap; 19 | import static java.util.Collections.reverseOrder; 20 | import static java.util.stream.Collectors.*; 21 | 22 | /* 23 | This variation of Example_03_Top10 does not just take the first elements of the last word list and ignores the rest 24 | but includes all elements. This might lead to a top 10 with 11 elements because the 10th and 11th element have both 25 | the same frequency. 26 | E.g. 27 | ... 28 | top10={42=[the], 39=[swallowed], 38=[she], 23=[to], 21=[catch], 14=[a, fly, that], 13=[and], 12=[spider, wiggled]} 29 | top09={42=[the], 39=[swallowed], 38=[she], 23=[to], 21=[catch], 14=[a, fly, that], 13=[and]} 30 | top08={42=[the], 39=[swallowed], 38=[she], 23=[to], 21=[catch], 14=[a, fly, that]} 31 | top07={42=[the], 39=[swallowed], 38=[she], 23=[to], 21=[catch], 14=[a, fly, that]} 32 | top06={42=[the], 39=[swallowed], 38=[she], 23=[to], 21=[catch], 14=[a, fly, that]} 33 | top05={42=[the], 39=[swallowed], 38=[she], 23=[to], 21=[catch]} 34 | ... 35 | 36 | This was my second (better) attempt to find a solution. 37 | */ 38 | public class Example_03b_Top10 { 39 | public static void main(String[] args) throws IOException { 40 | // with one stream 41 | List lines = Files.readAllLines(Path.of("rhyme.txt")); 42 | SortedMap> top10Plus = lines.stream() 43 | .filter(line -> !line.isEmpty()) 44 | .map(line -> line.replaceAll("[\\!|\\.|\\-|\\,|\\;]", "")) 45 | .flatMap(line -> Arrays.stream(line.split("\\s+"))) 46 | .collect(groupingBy(s -> s, () -> new TreeMap<>(CASE_INSENSITIVE_ORDER), counting())) 47 | .entrySet().stream() 48 | .collect(collectingAndThen(groupingBy(Map.Entry::getValue, () -> new TreeMap<>(reverseOrder()), 49 | mapping(Map.Entry::getKey, toList())), 50 | map -> map.keySet().stream() 51 | .map(map::headMap) 52 | .filter(headMap -> (10 <= sumSizesOfValues(headMap))) 53 | .map(TreeMap::new) 54 | .findFirst().orElse(new TreeMap<>(map)))); 55 | System.out.println("top10=" + top10Plus); 56 | System.out.println(); 57 | 58 | // with several streams 59 | Map frequenciesByWord = lines.stream() 60 | .filter(line -> !line.isEmpty()) 61 | .map(line -> line.replaceAll("[\\!|\\.|\\-|\\,|\\;]", "")) 62 | .flatMap(line -> Arrays.stream(line.split("\\s+"))) 63 | .collect(groupingBy(s -> s, () -> new TreeMap<>(CASE_INSENSITIVE_ORDER), counting())); 64 | System.out.println("frequenciesByWord=" + frequenciesByWord); 65 | System.out.println(); 66 | 67 | SortedMap> wordsByFrequency = 68 | frequenciesByWord.entrySet() 69 | .stream() 70 | .collect(groupingBy(Map.Entry::getValue, () -> new TreeMap<>(reverseOrder()), 71 | mapping(Map.Entry::getKey, toList()))); 72 | System.out.println("wordsByFrequency=" + wordsByFrequency); 73 | System.out.println(); 74 | 75 | SortedMap> onlyTop10Plus = 76 | wordsByFrequency.keySet().stream() 77 | .map(wordsByFrequency::headMap) 78 | .filter(headMap -> (10 <= sumSizesOfValues(headMap))) 79 | .map(TreeMap::new) 80 | .findFirst().orElse(new TreeMap<>(wordsByFrequency)); 81 | System.out.println("onlyTop10=" + onlyTop10Plus); 82 | System.out.println(); 83 | } 84 | 85 | public static long sumSizesOfValues(SortedMap> map) { 86 | return map.values().stream().mapToLong(List::size).sum(); 87 | } 88 | } 89 | -------------------------------------------------------------------------------- /src/main/java/net/mirwaldt/streams/Example_04_FilterMapGroupingBy.java: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright (c) 2022, Michael Mirwaldt. All rights reserved. 3 | * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. 4 | * 5 | * Creative Commons License 6 | *
This work is licensed under a 7 | * Creative Commons Attribution-NonCommercial-NoDerivatives 4.0 International License. 8 | */ 9 | 10 | package net.mirwaldt.streams; 11 | 12 | import java.util.List; 13 | 14 | import static java.util.stream.Collectors.groupingBy; 15 | import static java.util.stream.Collectors.toList; 16 | 17 | public class Example_04_FilterMapGroupingBy { 18 | public static void main(String[] args) { 19 | var names = List.of("Heinz", "Michael", "Brian", "Marc", "Kurt"); 20 | var selectedUpperCaseNamesByFirstLetter = names.stream() 21 | .filter(name -> 'J' <= name.charAt(0)) // range J-Z 22 | .map(String::toUpperCase) 23 | .collect(groupingBy(name -> name.substring(0, 1), toList())); 24 | System.out.println(selectedUpperCaseNamesByFirstLetter); 25 | } 26 | } 27 | -------------------------------------------------------------------------------- /src/main/java/net/mirwaldt/streams/Example_05_CamelCase.java: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright (c) 2022, Michael Mirwaldt. All rights reserved. 3 | * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. 4 | * 5 | * Creative Commons License 6 | *
This work is licensed under a 7 | * Creative Commons Attribution-NonCommercial-NoDerivatives 4.0 International License. 8 | */ 9 | 10 | package net.mirwaldt.streams; 11 | 12 | import java.util.Arrays; 13 | 14 | import static java.util.stream.Collectors.joining; 15 | 16 | public class Example_05_CamelCase { 17 | public static void main(String[] args) { 18 | String moduleName = "project-process-create-account"; 19 | String camelCaseName = Arrays.stream(moduleName.split("-")) 20 | .skip(2) 21 | .map(name -> name.substring(0, 1).toUpperCase() + name.substring(1)) 22 | .collect(joining()) + "Process"; // CreateAccountProcess 23 | System.out.println(camelCaseName); 24 | } 25 | } 26 | -------------------------------------------------------------------------------- /src/main/java/net/mirwaldt/streams/Example_06_allMatch.java: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright (c) 2022, Michael Mirwaldt. All rights reserved. 3 | * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. 4 | * 5 | * Creative Commons License 6 | *
This work is licensed under a 7 | * Creative Commons Attribution-NonCommercial-NoDerivatives 4.0 International License. 8 | */ 9 | 10 | package net.mirwaldt.streams; 11 | 12 | import java.util.List; 13 | 14 | public class Example_06_allMatch { 15 | public static void main(String[] args) { 16 | var intsAsStrings = List.of("1", "2", "3", "5", "6", "8", "11"); 17 | System.out.println(String.join(" + ", intsAsStrings) + " = " + parseAndSumPositiveInts(intsAsStrings)); 18 | } 19 | 20 | public static int parseAndSumPositiveInts(List intsAsStrings) { 21 | if (intsAsStrings.stream().allMatch(str -> str.matches("\\d+"))) { 22 | return intsAsStrings.stream() 23 | .mapToInt(Integer::parseInt) 24 | .sum(); 25 | } else { 26 | String nonPositiveInt = intsAsStrings.stream() 27 | .filter(str -> !str.matches("\\d+")) 28 | .findFirst().get(); 29 | throw new IllegalArgumentException("'" + nonPositiveInt + "' is not a positive integer."); 30 | } 31 | } 32 | } 33 | -------------------------------------------------------------------------------- /src/main/java/net/mirwaldt/streams/Example_07_MergeMapsByMin.java: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright (c) 2022, Michael Mirwaldt. All rights reserved. 3 | * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. 4 | * 5 | * Creative Commons License 6 | *
This work is licensed under a 7 | * Creative Commons Attribution-NonCommercial-NoDerivatives 4.0 International License. 8 | */ 9 | 10 | package net.mirwaldt.streams; 11 | 12 | import java.util.Map; 13 | import java.util.SortedMap; 14 | import java.util.TreeMap; 15 | import java.util.stream.Stream; 16 | 17 | import static java.util.stream.Collectors.toMap; 18 | 19 | public class Example_07_MergeMapsByMin { 20 | public static void main(String[] args) { 21 | SortedMap leftMap = new TreeMap<>(Map.of(1, 3, 2, 1, 3, 4)); 22 | SortedMap rightMap = new TreeMap<>(Map.of(1, 2, 2, 3, 3, 4)); 23 | SortedMap mergedByMin = 24 | Stream.of(leftMap, rightMap) 25 | .flatMap(map -> map.entrySet().stream()) 26 | .collect(toMap(Map.Entry::getKey, 27 | Map.Entry::getValue, 28 | Math::min, 29 | TreeMap::new) 30 | ); // result : {1=2, 2=1, 3=4} 31 | System.out.println(mergedByMin); 32 | } 33 | } 34 | -------------------------------------------------------------------------------- /src/main/java/net/mirwaldt/streams/Example_08_PrintOutNamesInUpperCase.java: -------------------------------------------------------------------------------- 1 | package net.mirwaldt.streams; 2 | 3 | import java.util.List; 4 | 5 | public class Example_08_PrintOutNamesInUpperCase { 6 | public static void main(String[] args) { 7 | List names = List.of("Heinz", "Venkat", "Nicolai", "Michael"); 8 | names.stream() 9 | .map(String::toUpperCase) 10 | .forEach(System.out::println); 11 | /* 12 | result: 13 | HEINZ 14 | VENKAT 15 | NICOLAI 16 | MICHAEL 17 | */ 18 | } 19 | } 20 | -------------------------------------------------------------------------------- /src/main/java/net/mirwaldt/streams/Example_09_First100Primes.java: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright (c) 2022, Michael Mirwaldt. All rights reserved. 3 | * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. 4 | * 5 | * Creative Commons License 6 | *
This work is licensed under a 7 | * Creative Commons Attribution-NonCommercial-NoDerivatives 4.0 International License. 8 | */ 9 | 10 | package net.mirwaldt.streams; 11 | 12 | import java.util.stream.IntStream; 13 | 14 | public class Example_09_First100Primes { 15 | public static void main(String[] args) { 16 | var first100Primes = IntStream.iterate(2, i -> i + 1) 17 | .filter(i -> isPrime(i)) 18 | .limit(100) 19 | .boxed().toList(); 20 | System.out.println(first100Primes); 21 | } 22 | 23 | public static boolean isPrime(int n) { 24 | for (int i = 2; i < n; i++) { 25 | if(n % i == 0) { 26 | return false; 27 | } 28 | } 29 | return 1 < n; 30 | } 31 | } 32 | -------------------------------------------------------------------------------- /src/main/java/net/mirwaldt/streams/Example_10_MapMulti.java: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright (c) 2022, Michael Mirwaldt. All rights reserved. 3 | * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. 4 | * 5 | * Creative Commons License 6 | *
This work is licensed under a 7 | * Creative Commons Attribution-NonCommercial-NoDerivatives 4.0 International License. 8 | */ 9 | 10 | package net.mirwaldt.streams; 11 | 12 | import java.util.List; 13 | import java.util.function.IntConsumer; 14 | 15 | public class Example_10_MapMulti { 16 | public static void main(String[] args) { 17 | List intTree = List.of(1, List.of(2, 3), List.of(List.of(4, 5))); 18 | List intList = intTree.stream() 19 | .mapMultiToInt(Example_10_MapMulti::visit) 20 | .limit(4) 21 | .boxed() 22 | .toList(); 23 | System.out.println(intList); 24 | } 25 | 26 | public static void visit(Object node, IntConsumer downStream) { 27 | if (node instanceof Iterable iterable) { 28 | for (Object e : iterable) { 29 | visit(e, downStream); 30 | } 31 | } else if (node instanceof Integer i) { 32 | downStream.accept(i); 33 | } 34 | } 35 | } 36 | -------------------------------------------------------------------------------- /src/main/java/net/mirwaldt/streams/Example_11_BadForeach.java: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright (c) 2022, Michael Mirwaldt. All rights reserved. 3 | * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. 4 | * 5 | * Creative Commons License 6 | *
This work is licensed under a 7 | * Creative Commons Attribution-NonCommercial-NoDerivatives 4.0 International License. 8 | */ 9 | 10 | package net.mirwaldt.streams; 11 | 12 | import java.util.List; 13 | 14 | public class Example_11_BadForeach { 15 | public static void main(String[] args) { 16 | List ints = List.of(1,2,3,5,6,8,9); 17 | 18 | // flawed 19 | System.out.println("-".repeat(120)); 20 | ints.stream().forEach(i -> { 21 | System.out.println(i); 22 | System.out.println("-".repeat(120)); 23 | }); 24 | 25 | // better 26 | System.out.println("-".repeat(120)); 27 | for (Integer i : ints) { 28 | System.out.println(i); 29 | System.out.println("-".repeat(120)); 30 | } 31 | } 32 | } 33 | -------------------------------------------------------------------------------- /src/main/java/net/mirwaldt/streams/Example_12_EmptyStream.java: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright (c) 2022, Michael Mirwaldt. All rights reserved. 3 | * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. 4 | * 5 | * Creative Commons License 6 | *
This work is licensed under a 7 | * Creative Commons Attribution-NonCommercial-NoDerivatives 4.0 International License. 8 | */ 9 | 10 | package net.mirwaldt.streams; 11 | 12 | import java.util.stream.Stream; 13 | 14 | public class Example_12_EmptyStream { 15 | public static void main(String[] args) { 16 | Stream stream = Stream.empty() 17 | .filter(i -> i < 3) 18 | .map(Integer::toBinaryString); 19 | System.out.println(stream); // ReferencePipeline is created although useless for the empty stream 20 | } 21 | } 22 | -------------------------------------------------------------------------------- /src/main/java/net/mirwaldt/streams/Example_13_Iterator.java: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright (c) 2022, Michael Mirwaldt. All rights reserved. 3 | * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. 4 | * 5 | * Creative Commons License 6 | *
This work is licensed under a 7 | * Creative Commons Attribution-NonCommercial-NoDerivatives 4.0 International License. 8 | */ 9 | 10 | package net.mirwaldt.streams; 11 | 12 | import java.util.ArrayList; 13 | import java.util.Arrays; 14 | import java.util.List; 15 | import java.util.ListIterator; 16 | 17 | public class Example_13_Iterator { 18 | public static void main(String[] args) { 19 | List ints = new ArrayList<>(Arrays.asList(1, 2, 3, 5, 6, 8, 9)); 20 | ListIterator iterator = ints.listIterator(); 21 | int i = 1; 22 | while (iterator.hasNext()) { 23 | iterator.next(); 24 | if(i % 3 == 0) { iterator.remove(); } 25 | i++; 26 | } 27 | System.out.println(ints); 28 | } 29 | } 30 | -------------------------------------------------------------------------------- /src/main/java/net/mirwaldt/streams/Example_14_TransposeMatrix.java: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright (c) 2022, Michael Mirwaldt. All rights reserved. 3 | * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. 4 | * 5 | * Creative Commons License 6 | *
This work is licensed under a 7 | * Creative Commons Attribution-NonCommercial-NoDerivatives 4.0 International License. 8 | */ 9 | 10 | package net.mirwaldt.streams; 11 | 12 | import java.util.Arrays; 13 | 14 | public class Example_14_TransposeMatrix { 15 | public static void main(String[] args) { 16 | int[][] matrix = new int[][]{{1, 2, 3}, {4, 5, 6}, {7, 8, 9}}; 17 | 18 | System.out.println(Arrays.deepToString(matrix) 19 | .replace("], ", "]\n") 20 | .replace("[[", "[") 21 | .replace("]]", "]")); 22 | 23 | for (int r = 1; r < matrix.length; r++) { 24 | for (int c = 0; c < r; c++) { 25 | int temp = matrix[c][r]; 26 | matrix[c][r] = matrix[r][c]; 27 | matrix[r][c] = temp; 28 | } 29 | } 30 | 31 | System.out.println("-".repeat(120)); 32 | 33 | System.out.println(Arrays.deepToString(matrix) 34 | .replace("], ", "]\n") 35 | .replace("[[", "[") 36 | .replace("]]", "]")); 37 | } 38 | } 39 | -------------------------------------------------------------------------------- /src/main/java/net/mirwaldt/streams/Example_15_Fibonacci.java: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright (c) 2022, Michael Mirwaldt. All rights reserved. 3 | * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. 4 | * 5 | * Creative Commons License 6 | *
This work is licensed under a 7 | * Creative Commons Attribution-NonCommercial-NoDerivatives 4.0 International License. 8 | */ 9 | 10 | package net.mirwaldt.streams; 11 | 12 | import java.util.stream.IntStream; 13 | 14 | public class Example_15_Fibonacci { 15 | public static void main(String[] args) { 16 | System.out.println("fibonacciByStream(6)=" + fibonacciByStream(6)); 17 | System.out.println("fibonacciByLoop(6)=" + fibonacciByLoop(6)); 18 | } 19 | 20 | public static long fibonacciByStream(int n) { 21 | long[] results = IntStream.rangeClosed(3, n) 22 | .boxed() 23 | .reduce(new long[]{0, 1, 1}, 24 | (fib, i) -> { 25 | fib[i % 3] = fib[(i -1) % 3] + fib[(i - 2) % 3]; 26 | return fib; 27 | }, 28 | (a, b) -> null); 29 | return results[n % 3]; 30 | } 31 | 32 | public static long fibonacciByLoop(int n) { 33 | long[] fib = new long[]{0, 1, 1}; 34 | for (int i = 3; i <= n; i++) { 35 | fib[i % 3] = fib[(i - 1) % 3] + fib[(i - 2) % 3]; 36 | } 37 | return fib[n % 3]; 38 | } 39 | } 40 | -------------------------------------------------------------------------------- /src/main/java/net/mirwaldt/streams/Example_16_HandlingCheckedExceptions.java: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright (c) 2022, Michael Mirwaldt. All rights reserved. 3 | * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. 4 | * 5 | * Creative Commons License 6 | *
This work is licensed under a 7 | * Creative Commons Attribution-NonCommercial-NoDerivatives 4.0 International License. 8 | */ 9 | 10 | package net.mirwaldt.streams; 11 | 12 | import java.net.URL; 13 | import java.util.List; 14 | import java.util.function.Function; 15 | import java.util.stream.Stream; 16 | 17 | public class Example_16_HandlingCheckedExceptions { 18 | public static void main(String[] args) { 19 | List urlsFromSneakyThrow = Stream.of("http://www.wikipedia.de", "http://www.mozilla.org/") 20 | .map(sneakyThrow(URL::new)) 21 | .toList(); 22 | System.out.println(urlsFromSneakyThrow); 23 | 24 | System.out.println("-".repeat(120)); 25 | 26 | List urls = Stream.of("http://www.wikipedia.de", "http://www.mozilla.org/") 27 | .map(unchecked(URL::new)) 28 | .toList(); 29 | System.out.println(urls); 30 | } 31 | 32 | public interface ExceptionFunction { 33 | R apply(T t) throws Exception; 34 | } 35 | 36 | static Function unchecked(ExceptionFunction f) { 37 | return t -> { 38 | try { 39 | return f.apply(t); 40 | } catch (RuntimeException ex) { 41 | throw ex; 42 | } catch (Exception ex) { 43 | throw new RuntimeException(ex); 44 | } 45 | }; 46 | } 47 | 48 | static Function sneakyThrow(TFunction f) { 49 | return t -> { 50 | try { 51 | return f.apply(t); 52 | } catch (Exception ex) { 53 | return sneaky(ex); 54 | } 55 | }; 56 | } 57 | 58 | public interface TFunction { 59 | R apply(T t) throws Exception; 60 | } 61 | 62 | static R sneaky(Exception t) throws T { 63 | throw (T) t; 64 | } 65 | } 66 | -------------------------------------------------------------------------------- /src/main/java/net/mirwaldt/streams/Example_17_DebuggingWithPeek.java: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright (c) 2022, Michael Mirwaldt. All rights reserved. 3 | * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. 4 | * 5 | * Creative Commons License 6 | *
This work is licensed under a 7 | * Creative Commons Attribution-NonCommercial-NoDerivatives 4.0 International License. 8 | */ 9 | 10 | package net.mirwaldt.streams; 11 | 12 | import java.util.List; 13 | 14 | public class Example_17_DebuggingWithPeek { 15 | public static void main(String[] args) { 16 | var list = List.of(2, 3, 5, 7, 11, 13, 17, 19); 17 | var result = list.stream() 18 | .filter(i -> i < 14) 19 | .peek(i -> System.out.println("after filter(): " + i)) 20 | .map(Integer::toBinaryString) 21 | .peek(i -> System.out.println("after map(): " + i)) 22 | .toList(); 23 | System.out.println(result); 24 | } 25 | } 26 | -------------------------------------------------------------------------------- /src/main/resources/German.txt: -------------------------------------------------------------------------------- 1 | Ein Hund kam in die Küche 2 | und stahl dem Koch ein Ei, 3 | da nahm der Koch den Löffel 4 | und schlug den Hund zu Brei. 5 | Da kamen viele Hunde 6 | und gruben ihm ein Grab 7 | uns setzten ihm ein Denkmal, 8 | auf dem geschrieben stand: -------------------------------------------------------------------------------- /src/test/java/net/mirwaldt/streams/Example_14_Fibonacci_Test.java: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright (c) 2022, Michael Mirwaldt. All rights reserved. 3 | * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. 4 | * 5 | * Creative Commons License 6 | *
This work is licensed under a 7 | * Creative Commons Attribution-NonCommercial-NoDerivatives 4.0 International License. 8 | */ 9 | 10 | package net.mirwaldt.streams; 11 | 12 | import org.junit.jupiter.api.Assertions; 13 | import org.junit.jupiter.api.Test; 14 | 15 | import static org.junit.jupiter.api.Assertions.assertEquals; 16 | 17 | public class Example_14_Fibonacci_Test { 18 | @Test 19 | void test_fibonacciByLoop() { 20 | Assertions.assertEquals(0, Example_15_Fibonacci.fibonacciByLoop(0)); 21 | Assertions.assertEquals(1, Example_15_Fibonacci.fibonacciByLoop(1)); 22 | Assertions.assertEquals(1, Example_15_Fibonacci.fibonacciByLoop(2)); 23 | Assertions.assertEquals(2, Example_15_Fibonacci.fibonacciByLoop(3)); 24 | Assertions.assertEquals(3, Example_15_Fibonacci.fibonacciByLoop(4)); 25 | Assertions.assertEquals(5, Example_15_Fibonacci.fibonacciByLoop(5)); 26 | Assertions.assertEquals(8, Example_15_Fibonacci.fibonacciByLoop(6)); 27 | } 28 | 29 | @Test 30 | void test_fibonacciByStream() { 31 | Assertions.assertEquals(0, Example_15_Fibonacci.fibonacciByStream(0)); 32 | Assertions.assertEquals(1, Example_15_Fibonacci.fibonacciByStream(1)); 33 | Assertions.assertEquals(1, Example_15_Fibonacci.fibonacciByStream(2)); 34 | Assertions.assertEquals(2, Example_15_Fibonacci.fibonacciByStream(3)); 35 | Assertions.assertEquals(3, Example_15_Fibonacci.fibonacciByStream(4)); 36 | Assertions.assertEquals(5, Example_15_Fibonacci.fibonacciByStream(5)); 37 | Assertions.assertEquals(8, Example_15_Fibonacci.fibonacciByStream(6)); 38 | } 39 | } 40 | --------------------------------------------------------------------------------