First of all, assuming you are going to create a HashMap, your key class (NameAndAge) must override equals and hashCode().

Second of all, in order to be efficient, I suggest you first create a Map<String,NameAndSalary> from the second List:

Map<String,NameAndSalary> helper =
    nameAndSalaryList.stream()
                     .collect(Collectors.toMap(NameAndSalary::getName,
                                               Function.identity()));

Finally, you can create the Map you want:

Map<NameAndAge,NameAndSalary> output = 
    nameAndAgeList.stream()
                  .collect(Collectors.toMap(Function.identity(),
                                            naa->helper.get(naa.getName())));
Answer from Eran on Stack Overflow
🌐
CodingTechRoom
codingtechroom.com › question › create-map-from-lists-java8-streams
How to Create a Map from Two Lists Using Common Conditions in Java 8 Streams - CodingTechRoom
... List<String> keys = Arrays.asList("A", "B", "C"); List<Integer> values = Arrays.asList(1, 2, 3); Map<String, Integer> resultMap = IntStream.range(0, keys.size()) .boxed() .collect(Collectors.toMap(keys::get, values::get)); // ResultMap: ...
Discussions

Creating Map composed of 2 Lists using stream().collect in Java - Stack Overflow
4 How to create a map from list with java-streams? ... Given an integer, find where it starts and ends in a sorted array in logarithmic time (Java) - Take II More on stackoverflow.com
🌐 stackoverflow.com
dictionary - What is the best way to combine two lists into a map in Java? - Stack Overflow
Why not use two normal iterators instead? 2017-05-23T16:28:14.783Z+00:00 ... I felt like having a library-like routine is in order to get a map from list elements. But maybe it is an overkill. 2017-05-24T13:04:28.283Z+00:00 ... Save this answer. ... Show activity on this post. With Java 8, I would ... More on stackoverflow.com
🌐 stackoverflow.com
java - Create map of matching elements in two lists - Stack Overflow
I have two lists. I want to create a map which will have true for the matching element and false for the unique one in java 8. Eg. Input- List 1 = [A,B,C,D] List 2 = [B,C,Y,Z] Output- Map: ... More on stackoverflow.com
🌐 stackoverflow.com
lambda - Java 8 : Iterate from 2 lists and create a Map<String, Custom Object> - Stack Overflow
I have a list of class A and class B with no duplicate elements. "code" attribute will be same across both class A and B. I want to convert them to Map using java 8 stre... More on stackoverflow.com
🌐 stackoverflow.com
🌐
Baeldung
baeldung.com › home › java › java collections › java map › combining two lists into a map in java
Combining Two Lists Into a Map in Java | Baeldung
June 27, 2025 - As the example above shows, we create a new HashMap called result. We then iterate through each element in KEY_LIST using a for loop, and for each element, we retrieve the corresponding element from VALUE_LIST using the same index i. Then, the put() method fills the key-value pair into the result map. Stream API provides many concise and efficient ways to manipulate Java collections. So next, let’s use the Java Stream API to associate two ...
Top answer
1 of 16
94

Been a while since this question was asked but these days I'm partial to something like:

public static <K, V> Map<K, V> zipToMap(List<K> keys, List<V> values) {
    return IntStream.range(0, keys.size()).boxed()
            .collect(Collectors.toMap(keys::get, values::get));
}

For those unfamiliar with streams, what this does is gets an IntStream from 0 to the length, then boxes it, making it a Stream<Integer> so that it can be transformed into an object, then collects them using Collectors.toMap which takes two suppliers, one of which generates the keys, the other the values.

This could stand some validation (like requiring keys.size() be less than values.size()) but it works great as a simple solution.

EDIT: The above works great for anything with constant time lookup, but if you want something that will work on the same order (and still use this same sort of pattern) you could do something like:

public static <K, V> Map<K, V> zipToMap(List<K> keys, List<V> values) {
    Iterator<K> keyIter = keys.iterator();
    Iterator<V> valIter = values.iterator();
    return IntStream.range(0, keys.size()).boxed()
            .collect(Collectors.toMap(_i -> keyIter.next(), _i -> valIter.next()));
}

The output is the same (again, missing length checks, etc.) but the time complexity isn't dependent on the implementation of the get method for whatever list is used.

2 of 16
53

I'd often use the following idiom. I admit it is debatable whether it is clearer.

Iterator<String> i1 = names.iterator();
Iterator<String> i2 = things.iterator();
while (i1.hasNext() && i2.hasNext()) {
    map.put(i1.next(), i2.next());
}
if (i1.hasNext() || i2.hasNext()) complainAboutSizes();

It has the advantage that it also works for Collections and similar things without random access or without efficient random access, like LinkedList, TreeSets or SQL ResultSets. For example, if you'd use the original algorithm on LinkedLists, you've got a slow Shlemiel the painter algorithm which actually needs n*n operations for lists of length n.

As 13ren pointed out, you can also use the fact that Iterator.next throws a NoSuchElementException if you try to read after the end of one list when the lengths are mismatched. So you'll get the terser but maybe a little confusing variant:

Iterator<String> i1 = names.iterator();
Iterator<String> i2 = things.iterator();
while (i1.hasNext() || i2.hasNext()) map.put(i1.next(), i2.next());
🌐
CodingTechRoom
codingtechroom.com › question › how-to-create-a-map-from-two-lists-in-java-using-stream-collect
How to Create a Map from Two Lists Using Java Streams? - CodingTechRoom
import java.util.Arrays; import java.util.List; import java.util.Map; import java.util.stream.Collectors; import java.util.stream.IntStream; public class MapFromLists { public static void main(String[] args) { List<String> keys = Arrays.asList("key1", "key2", "key3"); List<Integer> values = Arrays.asList(1, 2, 3); Map<String, Integer> resultMap = IntStream.range(0, keys.size()).boxed() .collect(Collectors.toMap(keys::get, values::get)); System.out.println(resultMap); } } The need to combine two separate lists into a single key-value pair collection.
🌐
Baeldung
baeldung.com › home › java › java collections › java map › how to convert list to map in java
How to Convert List to Map in Java | Baeldung
April 4, 2025 - Since its introduction in Java 8, the Stream API has become a staple of Java development. The basic operations like iterating, filtering, mapping sequences of elements are deceptively simple to use. But these can also be overused and fall into some common pitfalls. To get a better understanding on how Streams work and how to combine them with other language features, check out our guide to Java Streams: ... Yes, Spring Security can be complex, from the more advanced functionality within the Core to the deep OAuth support in the framework.
Find elsewhere
🌐
Javathinking
javathinking.com › blog › convert-2-list-to-map-java-8
Converting Two Lists to a Map in Java 8 | JavaThinking.com
July 21, 2025 - When converting two lists to a map, we can use the Stream class to iterate over the elements of the lists and transform them into key - value pairs. Lambda expressions are a concise way to represent anonymous functions in Java. They are used in conjunction with the Stream API to define operations ...
🌐
Electro4u
electro4u.net › blog › combining-two-lists-into-a-map-in-java---1294
Combining Two Lists into a Map in Java |
You can use the java.util.stream.Collectors.toMap method to do this. The following code shows an example of how this can be done: List<String> list1 = Arrays.asList("a", "b", "c"); List<Integer> list2 = Arrays.asList(1, 2, 3); Map<String, Integer> map = list1.stream().collect(Collectors.toMap( ...
🌐
CodingTechRoom
codingtechroom.com › tutorial › java-java-combine-two-lists-into-map
Java: How to Combine Two Lists Into a Map - CodingTechRoom
import java.util.HashMap; import java.util.Map; // Inside main method Map<String, Integer> map = new HashMap<>(); for (int i = 0; i < keys.size(); i++) { map.put(keys.get(i), values.get(i)); } System.out.println(map); // Output: {one=1, two=2, three=3} For a more modern and functional approach, ...
🌐
Stack Overflow
stackoverflow.com › questions › 50165008 › create-map-from-two-lists-with-key-and-value-as-same-object
java - Create map from two lists with key and value as same object - Stack Overflow
3 Java 8: Convert 2 Lists into List of Map · 2 Create Map based on two other maps in Java · 6 Merge two lists of objects into Map having value as different object in java 8 · 9 generating map from list of objects having a map using java lambda8 · 7 Using Java lambda to build map from two maps ·
Top answer
1 of 2
7

This should be optimal. You first build a map from the currencies to their commercial banks. Then you run through your centrals building a map from commercial to central (looked up in the first map).

    List<CurrencyItem> currenciesByCommercialBank = new ArrayList<>();
    List<CurrencyItem> currenciesByCentralBank = new ArrayList<>();
    // Build my lookup from CurrencyName to CommercialBank.
    Map<CurrencyName, CurrencyItem> commercials = currenciesByCommercialBank
            .stream()
            .collect(
                    Collectors.toMap(
                            // Map from currency name.
                            ci -> ci.getName(),
                            // To the commercial bank itself.
                            ci -> ci));
    Map<CurrencyItem, CurrencyItem> commercialToCentral = currenciesByCentralBank
            .stream()
            .collect(
                    Collectors.toMap(
                            // Map from the equivalent commercial
                            ci -> commercials.get(ci.getName()),
                            // To this central.
                            ci -> ci
                    ));
2 of 2
4

The following code is O(n2), but it should be OK for small collections (which your lists probably are):

return currenciesByCommercialBank
    .stream()
    .map(c ->
        new AbstractMap.SimpleImmutableEntry<>(
            c, currenciesByCentralBank.stream()
                                      .filter(c2 -> c.currencyName == c2.currencyName)
                                      .findFirst()
                                      .get()))
    .collect(Collectors.toMap(Map.Entry::getKey, Map.Entry::getValue));
  }

The above is appropriate if you want to assert that currenciesByCentralBank contains a match for each item in currenciesByCommercialBank. If the two lists can have mismatches, then the following would be appropriate:

currenciesByCommercialBank
    .stream()
    .flatMap(c ->
        currenciesByCentralBank.stream()
                               .filter(c2 -> c.currencyName == c2.currencyName)
                               .map(c2 -> new AbstractMap.SimpleImmutableEntry<>(c, c2)))
    .collect(Collectors.toMap(Map.Entry::getKey, Map.Entry::getValue));

In this case the map will contain all the matches and won't complain about missing entries.

Top answer
1 of 3
3

As has been suggested, using a Map<String,List<Employee>> is probably what you want. I constructed a small class and an example to illustrate the process.

      List<Employee> emps = List.of(
            new Employee("001", "Jim"),
            new Employee("002", "Bob"),
            new Employee("001", "June"),
            new Employee("002", "Jean"));

     // For each employee, using departmentId as the key, construct
     // a map containing lists of all employees that have that ID

      Map<String, List<Employee>> empMap = 
          emps
              .stream()
              .collect(
                  Collectors.groupingBy(emp -> emp.departmentId)
              );

      for (Entry<?, ?> e : empMap.entrySet()) {
         System.out.println(e.getKey() + "-->" + e.getValue());
      }



      class Employee {
          public String departmentId;
          public String name;
    
          public Employee(String departmentId, String name) {
             this.departmentId = departmentId;
             this.name = name;
          }
          public String toString() {
             return "(" + departmentId + " " + name + ")";
          }
       }

This displays

001-->[(001 Jim), (001 June)]
002-->[(002 Bob), (002 Jean)]

Another option, which would do the exact same thing is as follows:

This creates an empty map. Then it iterates over the list of employees and computes whether the value for the key exists. If it does, it returns the list and adds the entry to that list. If it doesn't, it then creates the new ArrayList and then adds the employee for that list, storing the list in the provided key.

     Map<String, List<Employee>> emp2 = new HashMap<>();
         for (Employee emp : emps) {
            emp2.compute(emp.departmentId,
               (ID, list) -> list == null ? new ArrayList<>()
                     : list).add(emp);
      }

In this case my preference would be the first method.

2 of 3
0

It is not possible to do this. Because Map can not have duplicate key. You can create Map<String,List<Employee>> by using Collectors.groupingBy()

🌐
amitph
amitph.com › home › java › examples of converting list to map using streams
Examples of Converting List to Map using Streams | amitph
November 22, 2024 - More on Java 8 · Avoid ... to Java 8 Lambda Expressions (old) The Java Stream Collectors.toMap() is a convenient method for creating maps....