Java8: Using Function::identity in Collectors.toMap(..) creates an argument mismatch error

佐手、 提交于 2019-12-23 22:36:34

问题


Given this simple Person POJO:

public class Person {
    private String id;
    private String name;

    public Person(String id, String name) {
        super();
        this.id = id;
        this.name = name;
    }

    public String getId() {
        return id;
    }

    public String getName() {
        return name;
    }
}

I would like to collect a Map<String, Person> where the key is the id of the Person.

I have tried to implement it like this:

import java.util.ArrayList;
import java.util.List;
import java.util.Map;
import java.util.function.Function;
import java.util.stream.Collectors;

public class CollectorMain {
    public static void main(String[] args) {
        List<Person> list = new ArrayList<>();
        list.add(new Person("312", "John"));
        list.add(new Person("454", "Alice"));
        list.add(new Person("712", "Bob"));

        Map<String, Person> map = list.stream()
               .collect(
                    Collectors.toMap(Person::getId, Function::identity) // COMPILE ERROR
               );
        System.out.println(map.size());
    }
}

But I get a compile error:

CollectorMain.java:[14,41] no suitable method found for toMap(Person::getId,Function::identity)
    method java.util.stream.Collectors.<T,K,U>toMap(java.util.function.Function<? super T,? extends K>,java.util.function.Function<? super T,? extends U>) is not applicable
      (cannot infer type-variable(s) T,K,U
        (argument mismatch; incompatible parameter types in method reference))
    method java.util.stream.Collectors.<T,K,U>toMap(java.util.function.Function<? super T,? extends K>,java.util.function.Function<? super T,? extends U>,java.util.function.BinaryOperator<U>) is not applicable
      (cannot infer type-variable(s) T,K,U
        (actual and formal argument lists differ in length))
    method java.util.stream.Collectors.<T,K,U,M>toMap(java.util.function.Function<? super T,? extends K>,java.util.function.Function<? super T,? extends U>,java.util.function.BinaryOperator<U>,java.util.function.Supplier<M>) is not applicable
      (cannot infer type-variable(s) T,K,U,M
        (actual and formal argument lists differ in length))

As a solution I can replace Function::identity with this lambda p -> p like this:

Map<String, Person> map = list.stream()
    .collect(
        Collectors.toMap(Person::getId, p -> p)
    );

Is there a possibility to use Function::identity ?


回答1:


You should not use a method reference. You should use Function.identity().

If you use a method reference, you're basically trying to pass a Supplier<Function<T, T>>.

Map<String, Person> map = list.stream().collect(
    Collectors.toMap(Person::getId, Function.identity())
);


来源:https://stackoverflow.com/questions/50504572/java8-using-functionidentity-in-collectors-tomap-creates-an-argument-mism

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!