目录
测试类
student类
@Data
public class Student {
private String name;
private Integer age;
private Integer score;
public Student(String name,Integer age,Integer score){
this.name = name;
this.age =age;
this.score = score;
}
}
public class Test {
public static void main(String[] args) {
List<Student> stList = new ArrayList<>();
stList.add(new Student("AA",1,1));
stList.add(new Student("AA",1,1));
stList.add(new Student("BB",1,1));
stList.add(new Student("CC",1,null));
//TODO
}
}
使用中的坑
(1)toMap
使用stream很常用场景,就是把list转map, 很多时候,写法如下:
stList.stream().collect(Collectors.toMap(Student::getName, Function.identity()));
放到上面测试类执行,发现会报错Exception in thread "main" java.lang.IllegalStateException: Duplicate key Student(name=AA, age=1, score=1)
有key重复会报错,跟我们以为的后面出现会覆盖前面相同的key理解不同,现场环境有垃圾数据或者重复数据,这个错误很容易出现。
防止抛出写法:
stList.stream().collect(Collectors.toMap(Student::getName, Function.identity(),(a1,a2)->a1));
意思是,以第一次出现的值为准,如果有逻辑,可以自行修改取值逻辑
(2)使用mapToInt等做统计
如果求学生的总分数,很多人就这么写
int ss = stList.stream().mapToInt(Student::getScore).sum();
执行之后,发现报错
Exception in thread "main" java.lang.NullPointerException
at java.util.stream.ReferencePipeline$4$1.accept(ReferencePipeline.java:210)
如果不用stream,用普通的for循环统计总数,估计大家都不会忘记对getScore()进行判空,用stream求统计值,同样也要考虑空指针
int ss = stList.stream().filter(a->a!=null && a.getScore()!=null).mapToInt(Student::getScore).sum();