Search code examples
javajava-streamreduce

Merge two lists using collect


I have 2 lists.

List<String> names = Arrays.asList("A","B","C","D");
List<String> wife = Arrays.asList("E","F","G");

I have used reduce() to merge it to a single list.

Stream.of(names, wife)
                .reduce(new ArrayList<String>(), (list, val) -> {
                    list.addAll(val);
                    return list;
                }, 
               (list1, list2) -> {list1.addAll(list2); return list1; }));

How do I perform the same operation using

collect 

method. I don't want to use functions from Collectors.java class. Is it possible to do it?

I tried this

List.of(names, wife).stream()
                .collect(new ArrayList<List<String>>(), (l1, l2) -> l1.addAll(l2));

However, I see that the l2 is of type List but not l1. What is l1? I want to learn how the collect method works. Please help!


Solution

  • Per the Javadoc for Stream#collect, you can pass ArrayList::new, ArrayList::add, ArrayList::addAll to the method to create and populate a collection such as ArrayList.

    You could specify another concrete collection implementation besides ArrayList, what ever suits your needs.

    To join our two lists together, I use Stream.concat.

    List < String > first = List.of( "A" , "B" , "C" , "D" );
    List < String > second = List.of( "E" , "F" , "G" );
    
    List < String > result =
            Stream
                    .concat( first.stream( ) , second.stream( ) )
                    .collect( 
                            ArrayList :: new , 
                            ArrayList :: add , 
                            ArrayList :: addAll 
                    );
    

    But if you can accept any unmodifiable List, then it is simpler to call toList.

    List < String > result =
            Stream
                    .concat( first.stream( ) , second.stream( ) )
                    .toList( );
    

    For more on joining streams, see Merging Streams in Java by Baeldung.com.