How to transform a List to Map by using java 8 lambda and stream or Guava

1. Introduction

This post would demo how to transform a List to Map by using java 8 lambda and stream or Guava.

This example will include:

  • How to transform a List to Map by using java 7 old style
  • How to transform a List to Map by using Guava Maps.uniqueIndex and java 8 lambda
  • How to transform a List to Map by using java 8 stream

1. Environments

  • Java 1.8

2. Example codes

2.1 Setup a class to be used as POJO object

This is an inner class named Game,which has two properties: name and price.

private static class Game {
    private String name;
    private double price;

    public Game(String name, double price) {
        this.name = name;
        this.price = price;
    }

    @Override
    public String toString() {
        return "Game{" +
                "name='" + name + '\'' +
                ", price=" + price +
                '}';
    }

    public String getName() {
        return name;
    }

    public void setName(String name) {
        this.name = name;
    }

    public double getPrice() {
        return price;
    }

    public void setPrice(double price) {
        this.price = price;
    }
}
  • It has a constructor with params
  • It has a toString for print purpose

2.2 How to transform a List to Map by using java 7 old style

Before we try the java 8 style, let’s review the java 7 old style:

    private static Map<String,Game> transformNormal(List<Game> games) {
        Map<String,Game> result = new HashMap<>();
        for(Game game:games) {
            result.put(game.getName(),game);
        }
        return result;
    }

We just use the game’s name as the map key and the game object as the value,that is:

Game.getName() –> Game Object

2.3 How to transform a List to Map by using Guava Maps.uniqueIndex and java 8 lambda

Guava supply a uniqueIndex method to transform a List to a Map, the method is:

public static <K,V> ImmutableMap<K,V> uniqueIndex(Iterable values,Function<? super V,K> keyFunction)

Returns a map with the given values, indexed by keys derived from those values. In other words, each input value produces an entry in the map whose key is the result of applying keyFunction to that value. These entries appear in the same order as the input values.

It just need two params:

  • The values, may be a List
  • The keyFunction, tranform from the value to a Key

Add the guava dependency to pom.xml

<dependency>
    <groupId>com.google.guava</groupId>
    <artifactId>guava</artifactId>
    <version>25.0-jre</version>
</dependency>

Then write the examples:

private static Map<String,Game> transformGuava(List<Game> games) {
    return Maps.uniqueIndex(games,game->game.getName());
}

private static Map<String,Game> transformGuava2(List<Game> games) {
    return Maps.uniqueIndex(games,Game::getName);
}

We write two examples:

  • The first one use Maps.uniqueIndex by supply a lambda expression
  • The second one use Maps.uniqueIndex by supply a method reference

2.4 How to transform a List to Map by using java 8 stream

    private static Map<String,Game> transformStream(List<Game> games) {
        return games.stream().collect(Collectors.toMap(Game::getName,game->game));
    }

Here we use the Collectors.toMap to do the trick, the Collectors.toMap method definition is:

public static <T, K, U> Collector<T, ?, Map<K,U» toMap(Function<? super T, ? extends K> keyMapper,Function<? super T, ? extends U> valueMapper)

Returns a Collector that accumulates elements into a Map whose keys and values are the result of applying the provided mapping functions to the input elements.

2.5 Run the examples

    private static void printMap(String title,Map<String,Game> map) {
        System.out.println("---"+title+"---");
        for(String key:map.keySet()) {
            System.out.println(key+"->"+map.get(key));
        }
        System.out.println();
    }

    public static void main(String[] args) {
        List<Game> games = Arrays.asList(
                new Game("game1",1.1),
                new Game("game2",2.1)
        );

        printMap("normal old transform",transformNormal(games));
        printMap("guava lambda transform",transformGuava(games));
        printMap("guava method reference transform",transformGuava2(games));
        printMap("stream transform",transformStream(games));
    }

And we got this result:

---normal old transform---
game1->Game{name='game1', price=1.1}
game2->Game{name='game2', price=2.1}

---guava lambda transform---
game1->Game{name='game1', price=1.1}
game2->Game{name='game2', price=2.1}

---guava method reference transform---
game1->Game{name='game1', price=1.1}
game2->Game{name='game2', price=2.1}

---stream transform---
game1->Game{name='game1', price=1.1}
game2->Game{name='game2', price=2.1}

As you can see, all kinds of transform has the same result.

3. summary

In this post we demo how to tranform a List to a Map by using various methods.You can find the whole code examples on github.

You can find detail documents about the java stream here: