Stream流根据属性去重
List根据属性去重
创建一个user集合
User user1 = new User("user1", 18, "AAA");
User user2 = new User("user2", 18, "BBB");
User user3 = new User("user3", 18, "AAA");
User user4 = new User("user4", 75, "CCC");
User user5 = new User("user5", 35, "AAA");
ArrayList<User> list = new ArrayList<>();
list.add(user1);
list.add(user2);
list.add(user3);
list.add(user4);
list.add(user5);
自定义Predict函数,使用filter()
写一个Predict
public class DistinctKeyUtil {
public static <T> Predicate<T> distinctByKey(Function<? super T, ?> keyExtractor) {
ConcurrentHashMap<Object, Boolean> map = new ConcurrentHashMap<>();
return t -> map.putIfAbsent(keyExtractor.apply(t), Boolean.TRUE) == null;
}
}
使用filter方法
/**
* 写一个Predict进行属性过滤
*/
//先过滤age在过滤hobby
List<User> result = list.stream()
.filter(DistinctKeyUtil.distinctByKey(n -> n.getAge()))
.filter(DistinctKeyUtil.distinctByKey(n -> n.getHobby()))
.collect(Collectors.toList());
result.forEach(System.out::println);
结果:
User{name='user1', age=18, hobby='AAA'}
User{name='user4', age=75, hobby='CCC'}
小结:
实质上是将每个元素都放到distinctByKey()中的ConcurrentHashMap作为key进行过滤,如果key不存在那么就加上去,如果已经存在了就不加。所以这种方式的过滤只保留第一个重复元素。
利用TreeSet
//过滤age
ArrayList<User> result2 = list.stream().collect(
Collectors.collectingAndThen(
Collectors.toCollection(
() -> new TreeSet<>(Comparator.comparing(o -> o.getAge()))), ArrayList::new));
result2.forEach(System.out::println);
结果与上面的一样
同时过滤两个属性
//age和hobby一起过滤
ArrayList<User> result1 = list.stream().collect(
Collectors.collectingAndThen(
Collectors.toCollection(
() -> new TreeSet<>(Comparator.comparing(o -> o.getHobby() + ";" + o.getAge()))), ArrayList::new)
);
result1.forEach(System.out::println);
结果:
User{name='user1', age=18, hobby='AAA'}
User{name='user5', age=35, hobby='AAA'}
User{name='user2', age=18, hobby='BBB'}
User{name='user4', age=75, hobby='CCC'}
小结:
TreeSet存储唯一的元素,并且按升序对元素进行排序。
Map:保证Key的唯一性
/**
* map 根据某属性过滤
*/
// Function.identity() 相等于 o->o
Map<String, User> map1 = list.stream().collect(Collectors.toMap(User::getHobby, Function.identity(), (t1, t2) -> t1));
Set<Map.Entry<String, User>> entries1 = map1.entrySet();
entries1.forEach(System.out::println);
结果:
AAA=User{name='user1', age=18, hobby='AAA'}
CCC=User{name='user4', age=75, hobby='CCC'}
BBB=User{name='user2', age=18, hobby='BBB'}
小结:
map可以选择保留重复属性中的前一条数据还是后一条:(t1, t2) -> t1)
Stream流根据属性去重的更多相关文章
- JDK 8 中Stream流中的去重的方法
JDK 8 中Stream流中去重的方法 1.简单的去重,可以使用distinct()方法去重,该方法是通过比较equals和hashcode值去去重, 2.复杂的去重, 例如,在一个JavaBean ...
- 【JDK8】JDK 8 中Stream流中的去重的方法
JDK 8 中Stream流中去重的方法 1.简单的去重,可以使用distinct()方法去重,该方法是通过比较equals和hashcode值去去重, 2.复杂的去重, 例如,在一个JavaBean ...
- Stream流用于按照对象中某一属性来对集合去重+简单数据类型集合的去重
上次对Stream流来进行分组的文章很多人看,想看的可以来这: Stream流来进行集合分组 这次小编又带来Stream的去重,话不多数,直接上代码: 这是对简单数据类型的去重 //字符串集合进行简单 ...
- List使用Stream流进行集合Collection的各种运算汇总:对BigDecimal求和,某个字段的和、最大值、最小值、平均值,字段去重,过滤等
写Java接口的朋友都知道,Java 8的更新,经常会用到过滤 list<Object> 里的数据,本文就对List使用Stream流进行集合Collection的各种运算做一个汇总! 优 ...
- (六)jdk8学习心得之Stream流
六.Stream流 1. 什么是stream流 现阶段,可以把stream流看成一个高级版的Iterator.普通的Iterator只能实现遍历,遍历做什么,就需要具体些功能代码函数了.而这个stre ...
- 简洁方便的集合处理——Java 8 stream流
背景 java 8已经发行好几年了,前段时间java 12也已经问世,但平时的工作中,很多项目的环境还停留在java1.7中.而且java8的很多新特性都是革命性的,比如各种集合的优化.lambda表 ...
- Java的Stream流式操作
前言 最近在实习,在公司看到前辈的一些代码,发现有很多值得我学习的地方,其中有一部分就是对集合使用Stream流式操作,觉得很优美且方便.所以学习一下Stream流,在这里记录一下. Stream是什 ...
- 再来看看Java的新特性——Stream流
半年前开始试着使用Java的新特性,给我印象最深的就是Stream流和Optional.其中Stream提高了看法效率,让代码看起来十分清爽. 为什么要使用流? 摘要中已经说明了,为了提高开发效率.流 ...
- 详解 stream流
在本人之前的博文中,我们学习了 I/O流.NIO流的相关概念. 那么,在JDK8的更新内容中,提出了一个新的流 -- stream流 那么,现在,本人就来讲解下这个流: 目录 stream流 常用AP ...
- List集合对象去重及按属性去重的8种方法-java基础总结系列第六篇
最近在写一些关于java基础的文章,但是我又不想按照教科书的方式去写知识点的文章,因为意义不大.基础知识太多了,如何将这些知识归纳总结,总结出优缺点或者是使用场景才是对知识的升华.所以我更想把java ...
随机推荐
- 学习记录--C++作业3
1.类是一个模板吗? 是:类模板是一个抽象的类,代表类的一般特性,可以用类模板来创建类,所有的类都有共有的特性. 4.函数模板的实例化是什么? 模板函数,即函数 3.关于cin和cout说法正确的: ...
- mybaits-plus 部分注解说明
参考: https://blog.csdn.net/qq_45684867/article/details/123951309
- Spring-设计模式
1.1开闭原则 开闭原则(open-closed principle,OCP)是指一个软件实体(如类,模块和函数)应该对扩展开放,对修改关闭.所谓的开闭,也正是对扩展和修改两个行为的一个原则. 强调用 ...
- 脏牛-Linux内核提权
漏洞范围 下载地址:https://github.com/FireFart/dirtycow 有一点可以在意,dirty.c内置在了kali中,使用命令searchsploit dirty可以搜索 也 ...
- 初认Spring
官网地址:https://spring.io/ Spring Framework的系统架构 1.Core Contiainer:核心容器 2.AOP:面向切片编程 3.Aspects:AOP思想实现 ...
- windows cmd基础命令
cmd md 新建目录rd 删除目录(非空目录)rd 删除目录下所有文件cd 改变当前目录cd .. 返回上一级目录cd \ 返回根目录d: 切换盘符到D盘dir 显示当前目录下的文件del 1.tx ...
- 如何基于Security框架兼容多套用户密码加密方式
一.说明 当已上线的系统存在使用其他的加密方式加密的密码数据,并且密码 不可逆 时,而新的数据采用了其他的加密方式,则需要同时兼容多种加密方式的密码校验. 例如下列几种情况: 旧系统用户的密码采用了 ...
- 分布式 WEB应用中Session(会话管理)的变迁之路
一.Session 介绍 Session 一词直译为 "会话",意指有始有终的一系列动作/消息.Session 是 Web 应用蓬勃发展的产物之一.在 Web 应用中隐含有&quo ...
- 阿里巴巴为什么建议使用BigDecimal进行浮点数运算
本文先引入一个例子,星期天你和女朋友去逛街,看到一家奶茶店.女朋友想喝奶茶了,你就去买了杯奶茶,然后你问了一下价格.店员说奶茶0.9元一杯.然后你给了1元钱.这个时候你忽然问了一下女友.服务员该找我们 ...
- Linux配置为代理服务器,代理微信
1.安装squid(全程使用root账号,如使用其他请注意权限问题) yum install squid 2.生成代理的账号密码 #如果没有htpasswd命令 先安装sudo yum install ...