为什么不使用合并函数就允许列表转换为Map?

hxzsmxv2  于 2021-07-06  发布在  Java
关注(0)|答案(2)|浏览(277)

由于对Java8比较陌生,我想知道为什么它允许第一个变体( merge 功能(不需要) Collectors.toMap() 使用时 List :

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

List 允许完全重复的值。想象一个开发人员使用 stream 转换 ListMap java 8将运行时公开为:

Exception in thread "main" java.lang.IllegalStateException: Duplicate key ...

这个场景不需要在编译时捕获吗?afaik,hashmap用来简单地替换旧的 Entry 当一个复制品 key 是放的。如果开发人员确定数据中存在重复的值,并希望将此异常作为警告来处理,那么他不首先使用 Set 而不是 List ? 例如:-

public class Employee{
    public String name;
    public String surname;
    public Employee(String firstname, String secondName) {
        this.name=firstname;this.surname=secondName;
    }
    public boolean equals(Object o){
        return (o instanceof Employee) && ((Employee)o).name.equals(this.name) && ((Employee)o).surname.equals(this.surname);
    }
    public int hashCode(){
        return (name+surname).toCharArray().length;
    }
    public String primaryKey(){
        return this.name;
    }
    public static void main(String[] args){
        Set<Employee> set = new HashSet<>();
        ArrayList<Employee> list = new ArrayList<>();
        Employee one = new Employee("firstname","secondName");
        Employee two = new Employee("firstname","secondName");
        list.add(one);list.add(two); //allows entirely duplicate
        Map<String,Employee> hashMap = new HashMap<>();
        for(Employee employee:list){
            //replace old employees in the order maintained by list before java 8
            hashMap.put(employee.primaryKey(), employee);
            //or may be use list inside some hashmap
        }
        set.add(one);set.add(two); //we can handle duplicates just by using sets
        Map<String,Employee> dontNeedListAsValues=set.stream().collect(Collectors.toMap(Employee::primaryKey,o->o));
        Map<String, Employee> needListAsValues=list.stream().collect(Collectors.toMap(Employee::primaryKey, o -> o)); //currently ALLOWED for LIST
    }
}
0dxa2lsx

0dxa2lsx1#

这不是一件事有几个原因:
只有一个 Stream 类型,两者之间相同 List 以及 Set .
只有一个 Collector 类型,如此不同 Collector 它不能只适用于特定类型的流。
最后,转换为 Set 当你知道这些键是唯一的时,对于这种特殊的情况来说是很重要的,而且通常是不值得的。

tpxzln5u

tpxzln5u2#

Collectors.toMap 已经有一个可以用于此的合并函数。

Map<String, Employee> // need proper value for accepting merge
     needListAsValues=list.stream().collect(Collectors.toMap(Employee::primaryKey, o -> o,
         (a,b) -> <merge BinaryOperator here>));

Map<String, List<Employee>> 
     needListAsValues=list.stream().collect(Collectors.groupingBy(Employee::primaryKey));

但是在编码中有很多情况是程序员自己来确保的 RunTime 例外情况不会发生或得到适当处理。

相关问题