{"id":3340,"date":"2025-12-24T10:00:42","date_gmt":"2025-12-24T15:00:42","guid":{"rendered":"https:\/\/www.mymiller.name\/wordpress\/?p=3340"},"modified":"2025-12-24T10:00:42","modified_gmt":"2025-12-24T15:00:42","slug":"java-collectors","status":"publish","type":"post","link":"https:\/\/www.mymiller.name\/wordpress\/lambda_stream\/java-collectors\/","title":{"rendered":"Java Collectors"},"content":{"rendered":"<p>Java 8 introduced the <code>Collectors<\/code> class, which provides a variety of collectors for use with streams. Collectors are used to accumulate the elements of a stream into a single result, such as a list or a map. In this article, we&#8217;ll take a closer look at the <code>Collectors<\/code> class and describe and give examples of all of its static methods.<\/p>\n<ol>\n<li><code>toList()<\/code><\/li>\n<\/ol>\n<p>The <code>toList()<\/code> method returns a collector that accumulates the elements of a stream into a new list.<\/p>\n<pre><code>List&lt;String&gt; list = Stream.of(\"one\", \"two\", \"three\").collect(Collectors.toList());\n<\/code><\/pre>\n<ol start=\"2\">\n<li><code>toSet()<\/code><\/li>\n<\/ol>\n<p>The <code>toSet()<\/code> method returns a collector that accumulates the elements of a stream into a new set.<\/p>\n<pre><code>Set&lt;String&gt; set = Stream.of(\"one\", \"two\", \"three\").collect(Collectors.toSet());\n<\/code><\/pre>\n<ol start=\"3\">\n<li><code>toMap()<\/code><\/li>\n<\/ol>\n<p>The <code>toMap()<\/code> method returns a collector that accumulates the elements of a stream into a new map. It takes two functions as arguments: a key mapping function and a value mapping function.<\/p>\n<pre><code>Map&lt;String, Integer&gt; map = Stream.of(\"one\", \"two\", \"three\").collect(Collectors.toMap(Function.identity(), String::length));\n<\/code><\/pre>\n<ol start=\"4\">\n<li><code>joining()<\/code><\/li>\n<\/ol>\n<p>The <code>joining()<\/code> method returns a collector that concatenates the elements of a stream into a single string, separated by a delimiter.<\/p>\n<pre><code>String joined = Stream.of(\"one\", \"two\", \"three\").collect(Collectors.joining(\", \"));\n<\/code><\/pre>\n<ol start=\"5\">\n<li><code>groupingBy()<\/code><\/li>\n<\/ol>\n<p>The <code>groupingBy()<\/code> method returns a collector that groups the elements of a stream into a map based on a classifier function.<\/p>\n<pre><code>Map&lt;Integer, List&lt;String&gt;&gt; map = Stream.of(\"one\", \"two\", \"three\")     .collect(Collectors.groupingBy(String::length));\n<\/code><\/pre>\n<ol start=\"6\">\n<li><code>summingInt()<\/code><\/li>\n<\/ol>\n<p>The <code>summingInt()<\/code> method returns a collector that calculates the sum of the elements of a stream.<\/p>\n<pre><code>int sum = IntStream.of(1, 2, 3, 4, 5).collect(Collectors.summingInt(Integer::intValue));\n<\/code><\/pre>\n<ol start=\"7\">\n<li><code>averagingInt()<\/code><\/li>\n<\/ol>\n<p>The <code>averagingInt()<\/code> method returns a collector that calculates the average of the elements of a stream.<\/p>\n<pre><code>double average = IntStream.of(1, 2, 3, 4, 5).collect(Collectors.averagingInt(Integer::intValue));\n<\/code><\/pre>\n<ol start=\"8\">\n<li><code>maxBy()<\/code><\/li>\n<\/ol>\n<p>The <code>maxBy()<\/code> method returns a collector that finds the maximum element of a stream, based on a comparator.<\/p>\n<pre><code>Optional&lt;Integer&gt; max = IntStream.of(1, 2, 3, 4, 5).boxed().collect(Collectors.maxBy(Comparator.naturalOrder()));\n<\/code><\/pre>\n<ol start=\"9\">\n<li><code>minBy()<\/code><\/li>\n<\/ol>\n<p>The <code>minBy()<\/code> method returns a collector that finds the minimum element of a stream, based on a comparator.<\/p>\n<pre><code>Optional&lt;Integer&gt; max = IntStream.of(1, 2, 3, 4, 5).boxed().collect(Collectors.maxBy(Comparator.naturalOrder()));\n<\/code><\/pre>\n<ol start=\"10\">\n<li><code>counting()<\/code><\/li>\n<\/ol>\n<p>The <code>counting()<\/code> method returns a collector that counts the elements of a stream.<\/p>\n<pre><code>long count = Stream.of(\"one\", \"two\", \"three\")     .collect(Collectors.counting());\n<\/code><\/pre>\n<ol start=\"11\">\n<li><code>partitioningBy()<\/code><\/li>\n<\/ol>\n<p>The <code>partitioningBy()<\/code> method returns a collector that partitions the elements of a stream into two groups based on a predicate.<\/p>\n<pre><code>Map&lt;Boolean, List&lt;Integer&gt;&gt; partitioned = IntStream.of(1, 2, 3, 4, 5).boxed().collect(Collectors.partitioningBy(n -&gt; n % 2 == 0));\n<\/code><\/pre>\n<ol start=\"12\">\n<li><code>toCollection()<\/code><\/li>\n<\/ol>\n<p>The <code>toCollection()<\/code> method returns a collector that accumulates the elements of a stream into a new collection of the specified type.<\/p>\n<pre><code>LinkedList&lt;String&gt; linkedList = Stream.of(\"one\", \"two\", \"three\").collect(Collectors.toCollection(LinkedList::new));\n<\/code><\/pre>\n<ol start=\"13\">\n<li><code>mapping()<\/code><\/li>\n<\/ol>\n<p>The <code>mapping()<\/code> method returns a collector that maps the elements of a stream before accumulating them.<\/p>\n<pre><code>List&lt;Integer&gt; lengths = Stream.of(\"one\", \"two\", \"three\").collect(Collectors.mapping(String::length, Collectors.toList()));\n<\/code><\/pre>\n<ol start=\"14\">\n<li><code>reducing()<\/code><\/li>\n<\/ol>\n<p>The <code>reducing()<\/code> method returns a collector that reduces the elements of a stream using a binary operator.<\/p>\n<pre><code>Optional&lt;Integer&gt; sum = Stream.of(1, 2, 3, 4, 5).collect(Collectors.reducing(Integer::sum));\n<\/code><\/pre>\n<ol start=\"15\">\n<li><code>teeing()<\/code><\/li>\n<\/ol>\n<p>The <code>teeing()<\/code> method returns a collector that applies two downstream collectors to the same stream and combines their results.<\/p>\n<pre><code>int sum = Stream.of(1, 2, 3, 4, 5)     \n\t.collect(Collectors.teeing( \n\t\tCollectors.summingInt(Integer::intValue),\n\t\tCollectors.counting(),\n\t\t(s, c) -&gt; s \/ c\n\t ));\n<\/code><\/pre>\n<ol start=\"16\">\n<li><code>summarizingInt()<\/code><\/li>\n<\/ol>\n<p>The <code>summarizingInt()<\/code> method returns a collector that calculates various statistics of the elements of a stream.<\/p>\n<pre><code>IntSummaryStatistics stats = IntStream.of(1, 2, 3, 4, 5).collect(Collectors.summarizingInt(Integer::intValue));\n<\/code><\/pre>\n<ol start=\"17\">\n<li><code>joining(CharSequence delimiter, CharSequence prefix, CharSequence suffix)<\/code><\/li>\n<\/ol>\n<p>The <code>joining()<\/code> method with arguments allows customizing the delimiter, prefix, and suffix of the concatenated string.<\/p>\n<pre><code>String joined = Stream.of(\"one\", \"two\", \"three\").collect(Collectors.joining(\", \", \"[\", \"]\"));\n<\/code><\/pre>\n<ol start=\"18\">\n<li><code>filtering()<\/code><\/li>\n<\/ol>\n<p>The <code>filtering()<\/code> method returns a collector that filters the elements of a stream before accumulating them.<\/p>\n<pre><code>List&lt;Integer&gt; evenNumbers = Stream.of(1, 2, 3, 4, 5).collect(Collectors.filtering(n -&gt; n % 2 == 0, Collectors.toList()));\n<\/code><\/pre>\n<ol start=\"19\">\n<li><code>flatMap()<\/code><\/li>\n<\/ol>\n<p>The <code>flatMap()<\/code> method returns a collector that applies a function to each element of a stream and flattens the results into a single stream.<\/p>\n<pre><code>List&lt;Integer&gt; allNumbers = Stream.of(\n\t\tArrays.asList(1, 2),\n\t\tArrays.asList(3, 4),\n\t\tArrays.asList(5)\n\t).collect(Collectors.flatMapping(List::stream, Collectors.toList()));\n<\/code><\/pre>\n<ol start=\"20\">\n<li><code>collectingAndThen()<\/code><\/li>\n<\/ol>\n<p>The <code>collectingAndThen()<\/code> method returns a collector that applies a final transformation function to the result of another collector.<\/p>\n<pre><code>List&lt;Integer&gt; doubled = Stream.of(1, 2, 3, 4, 5)\n\t.collect(Collectors.collectingAndThen(Collectors.toList(),\n\t\tlist -&gt; list.stream().map(n -&gt; n * 2)\n\t.collect(Collectors.toList())));\n<\/code><\/pre>\n<p>In conclusion, the <code>Collectors<\/code> class in Java provides a wide range of static methods that simplify the process of accumulating the elements of a stream into a collection or reducing them to a single value. With the help of these collectors, we can easily perform common operations like grouping, partitioning, counting, summing, averaging, joining, filtering, and mapping.<\/p>\n<p>It is important to note that the performance of these collectors can vary depending on the characteristics of the stream, such as size, order, and parallelism. Therefore, it is recommended to use the appropriate collector for the specific use case and to benchmark the performance for large or complex streams.<\/p>\n<p>I hope this article has helped you understand the various static methods available in the <code>Collectors<\/code> class and how to use them in your Java applications. With these powerful collectors, you can easily manipulate and transform the elements of a stream to meet your specific requirements. Happy coding!<\/p>\n","protected":false},"excerpt":{"rendered":"<p>Java 8 introduced the Collectors class, which provides a variety of collectors for use with streams. Collectors are used to accumulate the elements of a stream into a single result, such as a list or a map. In this article, we&#8217;ll take a closer look at the Collectors class and describe and give examples of [&hellip;]<\/p>\n","protected":false},"author":1,"featured_media":3344,"comment_status":"open","ping_status":"open","sticky":false,"template":"","format":"standard","meta":{"_coblocks_attr":"","_coblocks_dimensions":"","_coblocks_responsive_height":"","_coblocks_accordion_ie_support":"","_jetpack_newsletter_access":"","_jetpack_dont_email_post_to_subs":false,"_jetpack_newsletter_tier_id":0,"_jetpack_memberships_contains_paywalled_content":false,"_jetpack_feature_clip_id":0,"_jetpack_memberships_contains_paid_content":false,"footnotes":"","jetpack_publicize_message":"","jetpack_publicize_feature_enabled":true,"jetpack_social_post_already_shared":true,"jetpack_social_options":{"image_generator_settings":{"template":"highway","default_image_id":0,"font":"","enabled":false},"version":2},"jetpack_post_was_ever_published":false},"categories":[456],"tags":[],"series":[],"class_list":["post-3340","post","type-post","status-publish","format-standard","has-post-thumbnail","hentry","category-lambda_stream"],"jetpack_publicize_connections":[],"jetpack_featured_media_url":"https:\/\/i0.wp.com\/www.mymiller.name\/wordpress\/wp-content\/uploads\/2023\/06\/data-g271bb8554_640.jpg?fit=640%2C285&ssl=1","jetpack-related-posts":[{"id":3353,"url":"https:\/\/www.mymiller.name\/wordpress\/lambda_stream\/java-teeing-collectors\/","url_meta":{"origin":3340,"position":0},"title":"Java Teeing Collectors","author":"Jeffery Miller","date":"December 24, 2025","format":false,"excerpt":"Java 12 introduced a new collector called the Teeing collector. This collector allows you to process elements with two different collectors simultaneously and combine the results into a single output. In this article, we'll take a closer look at the Teeing collector and how you can use it in your\u2026","rel":"","context":"In &quot;Lambda's and Streams&quot;","block_context":{"text":"Lambda's and Streams","link":"https:\/\/www.mymiller.name\/wordpress\/category\/lambda_stream\/"},"img":{"alt_text":"","src":"https:\/\/i0.wp.com\/www.mymiller.name\/wordpress\/wp-content\/uploads\/2023\/06\/lost-places-g4dcac2ba2_640.jpg?fit=640%2C427&ssl=1&resize=350%2C200","width":350,"height":200,"srcset":"https:\/\/i0.wp.com\/www.mymiller.name\/wordpress\/wp-content\/uploads\/2023\/06\/lost-places-g4dcac2ba2_640.jpg?fit=640%2C427&ssl=1&resize=350%2C200 1x, https:\/\/i0.wp.com\/www.mymiller.name\/wordpress\/wp-content\/uploads\/2023\/06\/lost-places-g4dcac2ba2_640.jpg?fit=640%2C427&ssl=1&resize=525%2C300 1.5x"},"classes":[]},{"id":3951,"url":"https:\/\/www.mymiller.name\/wordpress\/java\/scaling-streams-mastering-virtual-threads-in-spring-boot-4-and-java-25\/","url_meta":{"origin":3340,"position":1},"title":"Scaling Streams: Mastering Virtual Threads in Spring Boot 4 and Java 25","author":"Jeffery Miller","date":"April 20, 2026","format":false,"excerpt":"As a software architect, I\u2019ve seen the industry shift from heavy platform threads to reactive streams, and finally to the \"best of both worlds\": Virtual Threads. With the recent release of Spring Boot 4.0 and Java 25 (LTS), Project Loom's innovations have officially become the bedrock of high-concurrency enterprise Java.\u2026","rel":"","context":"In &quot;JAVA&quot;","block_context":{"text":"JAVA","link":"https:\/\/www.mymiller.name\/wordpress\/category\/java\/"},"img":{"alt_text":"","src":"https:\/\/www.mymiller.name\/wordpress\/wp-content\/uploads\/2025\/12\/Gemini_Generated_Image_wqijejwqijejwqij-scaled.avif","width":350,"height":200,"srcset":"https:\/\/www.mymiller.name\/wordpress\/wp-content\/uploads\/2025\/12\/Gemini_Generated_Image_wqijejwqijejwqij-scaled.avif 1x, https:\/\/www.mymiller.name\/wordpress\/wp-content\/uploads\/2025\/12\/Gemini_Generated_Image_wqijejwqijejwqij-scaled.avif 1.5x, https:\/\/www.mymiller.name\/wordpress\/wp-content\/uploads\/2025\/12\/Gemini_Generated_Image_wqijejwqijejwqij-scaled.avif 2x, https:\/\/www.mymiller.name\/wordpress\/wp-content\/uploads\/2025\/12\/Gemini_Generated_Image_wqijejwqijejwqij-scaled.avif 3x"},"classes":[]},{"id":2404,"url":"https:\/\/www.mymiller.name\/wordpress\/lambda_stream\/using-collector-interface\/","url_meta":{"origin":3340,"position":2},"title":"Using java.util.stream.Collector","author":"Jeffery Miller","date":"April 20, 2026","format":false,"excerpt":"You will find plenty of articles on how to create your own Collector, and calling Streams.collect() with a collector to gather the data into a collection. Learn how to add a Collector interface to your code in order to make a collection.","rel":"","context":"In &quot;Lambda's and Streams&quot;","block_context":{"text":"Lambda's and Streams","link":"https:\/\/www.mymiller.name\/wordpress\/category\/lambda_stream\/"},"img":{"alt_text":"","src":"https:\/\/i0.wp.com\/www.mymiller.name\/wordpress\/wp-content\/uploads\/2018\/10\/attorney-2743547_640.jpg?fit=640%2C426&ssl=1&resize=350%2C200","width":350,"height":200,"srcset":"https:\/\/i0.wp.com\/www.mymiller.name\/wordpress\/wp-content\/uploads\/2018\/10\/attorney-2743547_640.jpg?fit=640%2C426&ssl=1&resize=350%2C200 1x, https:\/\/i0.wp.com\/www.mymiller.name\/wordpress\/wp-content\/uploads\/2018\/10\/attorney-2743547_640.jpg?fit=640%2C426&ssl=1&resize=525%2C300 1.5x"},"classes":[]},{"id":3179,"url":"https:\/\/www.mymiller.name\/wordpress\/java_extra\/understanding-json-data-processing-with-java-exploring-the-jsonfieldprocessor-class\/","url_meta":{"origin":3340,"position":3},"title":"Understanding JSON Data Processing with Java: Exploring the JsonFieldProcessor Class","author":"Jeffery Miller","date":"January 15, 2026","format":false,"excerpt":"In today's digital era, data comes in various formats, with JSON (JavaScript Object Notation) being one of the most popular for representing structured data. Manipulating and processing JSON data efficiently is crucial for many software applications, from web development to data analysis. In this article, we'll delve into the workings\u2026","rel":"","context":"In &quot;Java Extras&quot;","block_context":{"text":"Java Extras","link":"https:\/\/www.mymiller.name\/wordpress\/category\/java_extra\/"},"img":{"alt_text":"","src":"https:\/\/i0.wp.com\/www.mymiller.name\/wordpress\/wp-content\/uploads\/2024\/04\/data-7798787_640.png?fit=640%2C640&ssl=1&resize=350%2C200","width":350,"height":200,"srcset":"https:\/\/i0.wp.com\/www.mymiller.name\/wordpress\/wp-content\/uploads\/2024\/04\/data-7798787_640.png?fit=640%2C640&ssl=1&resize=350%2C200 1x, https:\/\/i0.wp.com\/www.mymiller.name\/wordpress\/wp-content\/uploads\/2024\/04\/data-7798787_640.png?fit=640%2C640&ssl=1&resize=525%2C300 1.5x"},"classes":[]},{"id":3148,"url":"https:\/\/www.mymiller.name\/wordpress\/java_tips\/java-tips-part-2\/","url_meta":{"origin":3340,"position":4},"title":"Java Tips Part 2","author":"Jeffery Miller","date":"December 24, 2025","format":false,"excerpt":"Continuing my Java Tips from experience that I have learned from code reviews to different programming tasks. Tip 6: Don't call .toString() on slf4j logging calls. So if you're following my other tips and using the formatting option of the logging messages like this: list.parallelStream().filter(item -> !item.contains(\"BOB\")).forEach(item -> logger.debug(\"Item: {}\u2026","rel":"","context":"In &quot;Java Tips&quot;","block_context":{"text":"Java Tips","link":"https:\/\/www.mymiller.name\/wordpress\/category\/java_tips\/"},"img":{"alt_text":"","src":"https:\/\/i0.wp.com\/www.mymiller.name\/wordpress\/wp-content\/uploads\/2021\/12\/sam-dan-truong-rF4kuvgHhU-unsplash-scaled-e1640791434235.jpg?fit=640%2C427&ssl=1&resize=350%2C200","width":350,"height":200,"srcset":"https:\/\/i0.wp.com\/www.mymiller.name\/wordpress\/wp-content\/uploads\/2021\/12\/sam-dan-truong-rF4kuvgHhU-unsplash-scaled-e1640791434235.jpg?fit=640%2C427&ssl=1&resize=350%2C200 1x, https:\/\/i0.wp.com\/www.mymiller.name\/wordpress\/wp-content\/uploads\/2021\/12\/sam-dan-truong-rF4kuvgHhU-unsplash-scaled-e1640791434235.jpg?fit=640%2C427&ssl=1&resize=525%2C300 1.5x"},"classes":[]},{"id":2459,"url":"https:\/\/www.mymiller.name\/wordpress\/java_tips\/not-returning-null\/","url_meta":{"origin":3340,"position":5},"title":"Not Returning Null","author":"Jeffery Miller","date":"April 20, 2026","format":false,"excerpt":"We all have done it, in fact, I'm in the process of changing my APIs over to not do.\u00a0 Returning NULL for a return type.\u00a0 After doing some work with streams, I see that return NULL often adds additional complexity to the code.\u00a0 In this article, we are going to\u2026","rel":"","context":"In &quot;Java Tips&quot;","block_context":{"text":"Java Tips","link":"https:\/\/www.mymiller.name\/wordpress\/category\/java_tips\/"},"img":{"alt_text":"","src":"https:\/\/i0.wp.com\/www.mymiller.name\/wordpress\/wp-content\/uploads\/2018\/11\/paper-3204064_640.jpg?fit=640%2C372&ssl=1&resize=350%2C200","width":350,"height":200,"srcset":"https:\/\/i0.wp.com\/www.mymiller.name\/wordpress\/wp-content\/uploads\/2018\/11\/paper-3204064_640.jpg?fit=640%2C372&ssl=1&resize=350%2C200 1x, https:\/\/i0.wp.com\/www.mymiller.name\/wordpress\/wp-content\/uploads\/2018\/11\/paper-3204064_640.jpg?fit=640%2C372&ssl=1&resize=525%2C300 1.5x"},"classes":[]}],"jetpack_sharing_enabled":true,"jetpack_likes_enabled":true,"_links":{"self":[{"href":"https:\/\/www.mymiller.name\/wordpress\/wp-json\/wp\/v2\/posts\/3340","targetHints":{"allow":["GET"]}}],"collection":[{"href":"https:\/\/www.mymiller.name\/wordpress\/wp-json\/wp\/v2\/posts"}],"about":[{"href":"https:\/\/www.mymiller.name\/wordpress\/wp-json\/wp\/v2\/types\/post"}],"author":[{"embeddable":true,"href":"https:\/\/www.mymiller.name\/wordpress\/wp-json\/wp\/v2\/users\/1"}],"replies":[{"embeddable":true,"href":"https:\/\/www.mymiller.name\/wordpress\/wp-json\/wp\/v2\/comments?post=3340"}],"version-history":[{"count":4,"href":"https:\/\/www.mymiller.name\/wordpress\/wp-json\/wp\/v2\/posts\/3340\/revisions"}],"predecessor-version":[{"id":3345,"href":"https:\/\/www.mymiller.name\/wordpress\/wp-json\/wp\/v2\/posts\/3340\/revisions\/3345"}],"wp:featuredmedia":[{"embeddable":true,"href":"https:\/\/www.mymiller.name\/wordpress\/wp-json\/wp\/v2\/media\/3344"}],"wp:attachment":[{"href":"https:\/\/www.mymiller.name\/wordpress\/wp-json\/wp\/v2\/media?parent=3340"}],"wp:term":[{"taxonomy":"category","embeddable":true,"href":"https:\/\/www.mymiller.name\/wordpress\/wp-json\/wp\/v2\/categories?post=3340"},{"taxonomy":"post_tag","embeddable":true,"href":"https:\/\/www.mymiller.name\/wordpress\/wp-json\/wp\/v2\/tags?post=3340"},{"taxonomy":"series","embeddable":true,"href":"https:\/\/www.mymiller.name\/wordpress\/wp-json\/wp\/v2\/series?post=3340"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}