Java中使用StreamAPI将对象List转Map的几种情景
1.使用对象中的属性构建映射Map
假设一个对象Person,其中有id、name两个属性,并且有对应关系。
@Data
@AllArgsConstructor
static class Person {
private String id;
private String Name;
}
现在将一个List<Person>转变为id与name的Map<String,String>。
如果personList中存在相同id的两个或多个对象,构建Map时会抛出key重复的异常,需要设置一个合并方法,将value合并(也可以是其他处理)
List<Person> personList = new ArrayList<>();
personList.add(new Person("1","张三"));
personList.add(new Person("1","李四"));
personList.add(new Person("1","王五"));
personList.add(new Person("2","王五"));
personList.add(new Person("3","赵六"));
Map<String,String> map = personList.stream()
.collect(Collectors.toMap(Person::getId,Person::getName,(v1,v2) -> v1 + '-' + v2));
System.out.println(map);
2.根据对象自定义Map中的Key与Value
代码:
Map<String,String> map = personList.stream()
.collect(Collectors.toMap(
item -> "编号:" + item.getId(),
item -> item.getName()+item.getId(),
(v1,v2) -> v1 + '-' + v2));
map.forEach((key,value) -> {
System.out.println(key+"\t"+value);
});
结果:
3.对象List先分组再映射为Map<key,List<Obj>>
假设Person对象中多个属性groupNo
private Integer groupNo;
根据Person中的groupNo属性将原始List分组,并返回Map<groupNo,List<Person>>
List<Person> personList = new ArrayList<>();
personList.add(new Person("1","张三",1));
personList.add(new Person("1","李四",1));
personList.add(new Person("1","王五",2));
personList.add(new Person("2","王五",2));
personList.add(new Person("3","赵六",3));
Map<Integer,List<Person>> map = personList.stream()
.collect(Collectors.groupingBy(Person::getGroupNo));
3.1 多个属性组合分组
再给Person类加一个性别 gender属性
private String gender;
List<Person> personList = new ArrayList<>();
personList.add(new Person("1","张三",1,"男"));
personList.add(new Person("1","李四",1,"女"));
personList.add(new Person("1","王五",2,"男"));
personList.add(new Person("2","王五",2,"变性人"));
personList.add(new Person("3","赵六",3,"武装直升机"));
Map<String,List<Person>> map = personList.stream()
.collect(Collectors.groupingBy(item -> item.getGroupNo()+"--"+item.getGender()));
map.forEach((key,value) -> {
System.out.println(key+"\t\t"+value);
});
3.2 分组后自定义Map中的Value
仅根据性别分组,并且Value只想要该分组的名称集合。实现如下
Map<String,List<String>> map = personList.stream()
.collect(Collectors.groupingBy(Person::getGender,Collectors.mapping(Person::getName,Collectors.toList())));
结果: