1.封装工具类
public class DeduplicationUtil {
public static <T> Predicate<T> distinctByKey(Function<? super T, ?> keyExtractor) {
Map<Object,Boolean> seen = new ConcurrentHashMap<>();
return t -> seen.putIfAbsent(keyExtractor.apply(t), Boolean.TRUE) == null;
}
}
2.简易学生对象
//偷懒用了lombok,自动生成getter和setter以及构造函数
@Data
@NoArgsConstructor
@AllArgsConstructor
public class Student {
private String id_;
private String name_;
}
3.使用junit测试
public class DemoTest {
@Test
public void test(){
Student student1 = new Student("1","aaa");
Student student2 = new Student("1","bbb");
Student student3 = new Student("1","ccc");
Student student4 = new Student("2","ccc");
ArrayList<Student> list = new ArrayList<>();
list.add(student1);
list.add(student2);
list.add(student3);
list.add(student4);
//使用封装方法的多字段
List<Student> collect = list.stream()
.filter(
DeduplicationUtil.distinctByKey(s -> s.getId_() + ";" + s.getName_())
).collect(Collectors.toList());
System.out.println(collect);
//多字段TreeSet
ArrayList<Student> collect1 = list.stream().collect(Collectors.collectingAndThen(
Collectors.toCollection(() -> new TreeSet<>(
Comparator.comparing(s->s.getId_() + ";" + s.getName_()))), ArrayList::new));
System.out.println(collect1);
}
}
单字段只要get一个不拼接即可,和distinct()方法区别是不需要重写hashcode以及equal方法,这样可以避免一些问题因为这些去重不完整。
参考文章:
https://blog.csdn.net/Kurry4ever_/article/details/109638367
https://www.jianshu.com/p/b1362370c77d
https://haiyoung.blog.csdn.net/article/details/80934467
https://blog.csdn.net/yojofly/article/details/100986216