1、前言
今日无事,记录下常用的一些Stream流操作。
很多案例只是提供思路,活学活用!
废话不多说直接上干货!
2、实体类
设置几个常见属性;
@Data
@AllArgsConstructor
@NoArgsConstructor
public class User implements Serializable {
private String userId;
private String userName;
private String areaCode;
private String areaName;
private Integer workDay;
}
3、具体操作
1、提取某一属性作为List 常用于数据处理时抽取特定字段
/*
*1、Stream 只取某一字段作为List sorted排序 distinct 去重
*/
List<String> areaCodes = userList.stream().map(User::getAreaCode).sorted().distinct().collect(Collectors.toList());
System.out.println(areaCodes);
List<String> names = userList.stream().map(User::getUserName).distinct().collect(Collectors.toList());
System.out.println(names);
效果:
2、stream 替换某一字段属性 常用于更改特定值
/*
2、stream 替换某一字段属性 替换workDay
*/
List<User> newUserList = userList.stream().map(a -> {
String xzqhdm = a.getAreaCode();
switch (xzqhdm) {
//雄安新区规划
case "130100":
a.setWorkDay(20);
break;
case "130200":
a.setWorkDay(22);
break;
}
return a;
}).collect(Collectors.toList());
newUserList.stream().forEach(a->{
System.out.println(a);
});
效果:
3、根据某字段排序
/*
3、根据某字段排序逆序
*/
List<User> reverseOrderCollect = userList.stream()
.sorted(Comparator.comparing(User::getUserId, Comparator.reverseOrder()))
.collect(Collectors.toList());
System.out.println("--排序逆序--");
reverseOrderCollect.stream().forEach(a->{
System.out.println(a);
});
List<User> sortCollect = userList.stream()
.sorted(Comparator.comparing(User::getUserId))
.collect(Collectors.toList());
System.out.println("--排序--");
sortCollect.stream().forEach(a->{
System.out.println(a);
});
效果:
4、筛选出符合条件数据 并取单一属性 常用与数据集筛选
/*
4、筛选出符合条件数据 并取单一属性 (筛选areacode为130100 的数据湖)
*/
List<User> user130100List = userList.stream().filter(a -> "130100".equals(a.getAreaCode())).collect(Collectors.toList());
System.out.println("--筛选出符合条件数据 并取单一属性--");
user130100List.stream().forEach(a->{
System.out.println(a);
});
效果:
5、根据某一字段是否包含字符分组 true、false 也可按照属性分组 常和6一起用处理数据
/*
5、根据某一字段是否包含字符分组 true、false
*/
Map<Boolean, List<User>> groupByMap = userList.stream().collect(Collectors.groupingBy(
a -> a.getUserName().contains("赵")
));
System.out.println("--根据某一字段是否包含字符分组-");
System.out.println(groupByMap.get(true));
System.out.println(groupByMap.get(false));
效果:
6、分组后遍历map执行方法
System.out.println("--根据某一字段是否包含字符分组-");
groupByMap.forEach((isZhao, list) ->
testZhao(isZhao, list)
);
private static void testZhao(Boolean isZhao, List<User> list){
if (isZhao){
list.stream().forEach(a->{
System.out.println("赵氏精英");
});
}else{
list.stream().forEach(a->{
System.out.println("非赵氏精英");
});
}
}
效果:
7、根据某一属性拼接逗号 常用于共有属性字段拼接
/*
7、 根据某一字段拼接","
*/
String allUserName = userList.stream()
.map(User::getUserName)
.collect(Collectors.joining(","));
System.out.println("--根据某一字段拼接\",\"--");
System.out.println(allUserName);
效果
8、根据某一字段分组
/*
8、根据某一字段分组
*/
Map<String, List<User>> groupingByMap = userList.stream()
.collect(Collectors.groupingBy(User::getAreaCode));
System.out.println("--根据某一字段分组--");
System.out.println(groupingByMap.get("130100"));
System.out.println(groupingByMap.get("130200"));
效果:
9、根据两个list集合某相同属性合并(赋值)
/*
9\根据某属性合并或替换两个list集合 (根据username 合并workday)
*/
userList = userList.stream().map(m -> {
newUserList.stream().filter(m2 -> Objects.equals(m.getUserName(), m2.getUserName())).forEach(
m2 -> {
m.setWorkDay(m2.getWorkDay()+m.getWorkDay());
m.setAreaCode(String.valueOf(m.getWorkDay()));
});
return m;
}).collect(Collectors.toList());
System.out.println("--根据某属性合并两个list集合--");
userList.stream().forEach(a->{
System.out.println(a);
});
效果:
10、根据某属性去重
System.out.println("--去重--");
userList.stream()
.filter(distinctByKey1(a->a.getWorkDay()))
.forEach(System.out::println);
static <T> Predicate<T> distinctByKey1(Function<? super T, ?> keyExtractor) {
Map<Object, Boolean> seen = new ConcurrentHashMap<>();
return t -> seen.putIfAbsent(keyExtractor.apply(t), Boolean.TRUE) == null;
}
效果:
11、根据某字段拆分为有序List
/*
11、根据某字段拆分为有序List
*/
System.out.println("--拆分有序list--");
userList.stream()
//默认hashmap 无序,需要设置有序map
.collect(Collectors.groupingBy(User::getAreaCode, LinkedHashMap::new, Collectors.toList()))
.values().stream().collect(Collectors.toList()).forEach(System.out::println);
效果:
4、完整代码
private static String[] NAME = new String[]{
"赵牛马", "钱牛马", "孙牛马", "李牛马", "周牛马"
};
public static void main(String[] args) {
List<String> nameList = Arrays.asList(NAME);
List<User> userList = new ArrayList<>();
User user;
for (int i = 0; i < 5; i++) {
user = new User();
user.setUserId(String.valueOf(i));
user.setUserName(nameList.get(i) + (i + 1) * 2);
if ((i & 1) == 0) {
user.setAreaCode("130200");
user.setAreaName("唐山");
} else {
user.setAreaCode("130100");
user.setAreaName("石家庄");
}
user.setWorkDay((i + 7) * (i + 1));
System.out.println(user);
userList.add(user);
}
/*
*1、Stream 只取某一字段作为List sorted排序
*/
List<String> years = userList.stream().map(User::getAreaCode).sorted().distinct().collect(Collectors.toList());
System.out.println(years);
List<String> names = userList.stream().map(User::getUserName).distinct().collect(Collectors.toList());
System.out.println(names);
/*
2、stream 替换某一字段属性 替换workDay
*/
List<User> newUserList = userList.stream().map(a -> {
String xzqhdm = a.getAreaCode();
switch (xzqhdm) {
//雄安新区规划
case "130100":
a.setWorkDay(33);
break;
case "130200":
a.setWorkDay(12);
break;
}
return a;
}).collect(Collectors.toList());
System.out.println("--替换某一字段属性 --");
newUserList.stream().forEach(a -> {
System.out.println(a);
});
/*
3、根据某字段排序逆序
*/
List<User> reverseOrderCollect = userList.stream()
.sorted(Comparator.comparing(User::getUserId, Comparator.reverseOrder()))
.collect(Collectors.toList());
System.out.println("--排序逆序--");
reverseOrderCollect.stream().forEach(a -> {
System.out.println(a);
});
List<User> sortCollect = userList.stream()
.sorted(Comparator.comparing(User::getUserId))
.collect(Collectors.toList());
System.out.println("--排序--");
sortCollect.stream().forEach(a -> {
System.out.println(a);
});
/*
4、筛选出符合条件数据 并取单一属性 (筛选areacode为130100 的数据湖)
*/
List<User> user130100List = userList.stream().filter(a -> "130100".equals(a.getAreaCode())).collect(Collectors.toList());
System.out.println("--筛选出符合条件数据 并取单一属性--");
user130100List.stream().forEach(a -> {
System.out.println(a);
});
/*
5、根据某一字段是否包含字符分组 true、false
*/
Map<Boolean, List<User>> groupByMap = userList.stream().collect(Collectors.groupingBy(
a -> a.getUserName().contains("赵")
));
System.out.println("--根据某一字段是否包含字符分组-");
System.out.println(groupByMap.get(true));
System.out.println(groupByMap.get(false));
/*
* 6、根据某一字段是否包含某字符串拆分并遍历
*/
System.out.println("--根据某一字段是否包含字符分组-");
groupByMap.forEach((isZhao, list) ->
testZhao(isZhao, list)
);
/*
7、 根据某一字段拼接","
*/
String allUserName = userList.stream()
.map(User::getUserName)
.collect(Collectors.joining(","));
System.out.println("--根据某一字段拼接\",\"--");
System.out.println(allUserName);
/*
8、根据某一字段分组
*/
Map<String, List<User>> groupingByMap = userList.stream()
.collect(Collectors.groupingBy(User::getAreaCode));
System.out.println("--根据某一字段分组--");
System.out.println(groupingByMap.get("130100"));
System.out.println(groupingByMap.get("130200"));
/*
9\根据某属性合并或替换两个list集合 (根据username 合并workday)
*/
userList = userList.stream().map(m -> {
newUserList.stream().filter(m2 -> Objects.equals(m.getUserName(), m2.getUserName())).forEach(
m2 -> {
m.setWorkDay(m2.getWorkDay() + m.getWorkDay());
m.setAreaCode(String.valueOf(m.getWorkDay()));
});
return m;
}).collect(Collectors.toList());
System.out.println("--根据某属性合并两个list集合--");
userList.stream().forEach(a -> {
System.out.println(a);
});
/*
10、去重
*/
System.out.println("--去重--");
userList.stream()
.filter(distinctByKey1(a -> a.getWorkDay()))
.forEach(System.out::println);
/*
11、根据某字段拆分为有序List
*/
System.out.println("--拆分有序list--");
userList.stream()
//默认hashmap 无序,需要设置有序map
.collect(Collectors.groupingBy(User::getAreaCode, LinkedHashMap::new, Collectors.toList()))
.values().stream().collect(Collectors.toList()).forEach(System.out::println);
}
private static void testZhao(Boolean isZhao, List<User> list) {
if (isZhao) {
list.stream().forEach(a -> {
System.out.println("赵氏精英");
});
} else {
list.stream().forEach(a -> {
System.out.println("非赵氏精英");
});
}
}
static <T> Predicate<T> distinctByKey1(Function<? super T, ?> keyExtractor) {
Map<Object, Boolean> seen = new ConcurrentHashMap<>();
return t -> seen.putIfAbsent(keyExtractor.apply(t), Boolean.TRUE) == null;
}