Java8 中 Stream 初试
作者:Geek_4bdbe1
- 2021 年 11 月 14 日
本文字数:5625 字
阅读完需:约 18 分钟
Stream 作为 Java8 的一大亮点,它与 java.io 包里的 InputStream 和 OutputStream 是完全不同的概念。它也不同于 StAX 对 XML 解析的 Stream,也不是 Amazon Kinesis 对大数据实时处理的 Stream。Java8 中的 Stream 是对容器对象功能的增强,它专注于对容器对象进行各种非常便利、高效的 聚合操作(aggregate operation),或者大批量数据操作 (bulk data operation)。Stream API 借助于同样新出现的 Lambda 表达式,极大的提高编程效率和程序可读性。同时,它提供串行和并行两种模式进行汇聚操作,并发模式能够充分利用多核处理器的优势,使用 fork/join 并行方式来拆分任务和加速处理过程。通常,编写并行代码很难而且容易出错, 但使用 Stream API 无需编写一行多线程的代码,就可以很方便地写出高性能的并发程序。所以说,Java8 中首次出现的 java.util.stream 是一个函数式语言+多核时代综合影响的产物。
package com.example.demo;
import lombok.*;
import java.math.BigDecimal;
/**
* TODO
*
* @author xuqinghai
* @version 1.0
* @date 2021/11/14 0014 下午 14:07
*/
@Getter
@Setter
@AllArgsConstructor
@ToString
@NoArgsConstructor
public class Person {
private long id;
private String name;
private String sex;
private int age;
private BigDecimal salary;
private String area;
}
复制代码
package com.example.demo;
import java.io.File;
import java.io.IOException;
import java.math.BigDecimal;
import java.nio.charset.StandardCharsets;
import java.nio.file.Files;
import java.nio.file.Path;
import java.util.*;
import java.util.stream.Collectors;
import java.util.stream.Stream;
/**
* TODO
*
* @author xuqinghai
* @version 1.0
* @date 2021/11/14 0014 下午 13:00
*/
public class MainTest {
private static List<Person> personList = new ArrayList<Person>(){{
add(new Person(1L,"张三","男",21,new BigDecimal("5000"),"北京"));
add(new Person(2L,"赵桦","女",25,new BigDecimal("6000"),"北京"));
add(new Person(3L,"许易","男",20,new BigDecimal("4500"),"杭州"));
add(new Person(4L,"张雷","女",28,new BigDecimal("8800"),"厦门"));
add(new Person(5L,"彭波波","男",38,new BigDecimal("25000"),"福州"));
add(new Person(6L,"李毅","男",29,new BigDecimal("9000"),"苏州"));
add(new Person(7L,"蒋蒋","男",31,new BigDecimal("15000"),"南京"));
add(new Person(8L,"花千骨","男",33,new BigDecimal("18000"),"深圳"));
add(new Person(9L,"桦省","男",35,new BigDecimal("21000"),"广州"));
add(new Person(10L,"慕容","女",19,new BigDecimal("21000"),"上海"));
}} ;
public static void main(String[] args) {
test09();
}
/**
* 文件流操作
* @author xuqinghai
* @date 2021/11/14 0014 下午 16:41
* @return void
*/
private static void test09() {
Path path = new File("D:/test.txt").toPath();
try {
Stream<String> lines = Files.lines(path, StandardCharsets.UTF_8);
lines.onClose(()->{
try {
Thread.sleep(30000L);
System.out.println("Done!");
} catch (InterruptedException e) {
e.printStackTrace();
}
}).forEach(System.out::println);
}catch(Exception e){
}
}
/**
* 提取/组合
* 流也可以进行合并、去重、限制、跳过等操作。
* @author xuqinghai
* @date 2021/11/14 0014 下午 16:14
* @return void
*/
private static void test08() {
String[] arr1 = { "a", "b", "c", "d" };
String[] arr2 = { "d", "e", "f", "g" };
Stream<String> stream1 = Stream.of(arr1);
Stream<String> stream2 = Stream.of(arr2);
List<Person> list1 = new ArrayList<Person>(){{
add(new Person(1L,"赵一","男",21,new BigDecimal("25600"),"上海"));
add(new Person(2L,"钱二","女",18,new BigDecimal("5600"),"厦门"));
add(new Person(3L,"孙三","男",26,new BigDecimal("18600"),"北京"));
}};
List<Person> list2 = new ArrayList<Person>(){{
add(new Person(5L,"周五","男",31,new BigDecimal("45600"),"苏州"));
add(new Person(4L,"李四","女",28,new BigDecimal("35600"),"杭州"));
add(new Person(3L,"孙三","男",26,new BigDecimal("18600"),"北京"));
}};
String names = Stream.concat(list1.stream(),list2.stream()).distinct().map(Person::getName).distinct().collect(Collectors.joining(","));
List<Person> pserlist = Stream.concat(list1.stream(),list2.stream()).collect(Collectors.toMap(Person::getName,l->l,(l1,l2)->{
l1.setAge(l1.getAge()-l2.getAge()>=0?l1.getAge():l2.getAge());
l1.setSalary(l1.getSalary().subtract(l2.getSalary()).longValue()>0?l1.getSalary():l2.getSalary());
return l1;
})).values().stream().sorted(Comparator.comparing(Person::getId)).collect(Collectors.toList());
// concat:合并两个流 distinct:去重
List<String> newList = Stream.concat(stream1, stream2).distinct().collect(Collectors.toList());
// limit:限制从流中获得前n个数据
List<Integer> collect = Stream.iterate(1, x -> x + 2).limit(10).collect(Collectors.toList());
// skip:跳过前n个数据
List<Integer> collect2 = Stream.iterate(1, x -> x + 2).skip(1).limit(5).collect(Collectors.toList());
System.out.println("流对象合并:"+names);
System.out.println("流对象合并:"+pserlist);
System.out.println("流合并:" + newList);
System.out.println("limit:" + collect);
System.out.println("skip:" + collect2);
}
/**
* 将员工按工资由高到低(工资一样则按年龄由大到小)排序
* @author xuqinghai
* @date 2021/11/14 0014 下午 16:11
* @return void
*/
private static void test07() {
// 按工资升序排序(自然排序)
List<String> newList = personList.stream().sorted(Comparator.comparing(Person::getSalary)).map(Person::getName)
.collect(Collectors.toList());
// 按工资倒序排序
List<String> newList2 = personList.stream().sorted(Comparator.comparing(Person::getSalary).reversed())
.map(Person::getName).collect(Collectors.toList());
// 先按工资再按年龄升序排序
List<String> newList3 = personList.stream()
.sorted(Comparator.comparing(Person::getSalary).thenComparing(Person::getAge)).map(Person::getName)
.collect(Collectors.toList());
// 先按工资再按年龄自定义排序(降序)
List<String> newList4 = personList.stream().sorted((p1, p2) -> {
if (p1.getSalary() == p2.getSalary()) {
return p2.getAge() - p1.getAge();
} else {
return p2.getSalary().subtract( p1.getSalary()).intValue();
}
}).map(Person::getName).collect(Collectors.toList());
System.out.println("按工资升序排序:" + newList);
System.out.println("按工资降序排序:" + newList2);
System.out.println("先按工资再按年龄升序排序:" + newList3);
System.out.println("先按工资再按年龄自定义降序排序:" + newList4);
}
/**
* 连接joining
* joining可以将stream中的元素用特定的连接符(没有的话,则直接连接)连接成一个字符串。
* @author xuqinghai
* @date 2021/11/14 0014 下午 16:08
* @return void
*/
private static void test06() {
String names = personList.stream().map(Person::getName).collect(Collectors.joining(","));
System.out.println("all name is "+ names);
}
/**
* 分组(partitioningBy/groupingBy)
* 分区:将stream按条件分为两个 Map,比如员工按薪资是否高于8000分为两部分。
* 分组:将集合分为多个Map,比如员工按性别分组。有单级分组和多级分组。
* @author xuqinghai
* @date 2021/11/14 0014 下午 15:58
* @return void
*/
private static void test05() {
// 将员工按薪资是否高于8000分组
Map<Boolean, List<Person>> part = personList.stream().collect(Collectors.partitioningBy(x -> x.getSalary().intValue() > 8000));
// 将员工按性别分组
Map<String, List<Person>> group = personList.stream().collect(Collectors.groupingBy(Person::getSex));
// 将员工先按性别分组,再按地区分组
Map<String, Map<String, List<Person>>> group2 = personList.stream().collect(Collectors.groupingBy(Person::getSex, Collectors.groupingBy(Person::getArea)));
System.out.println("员工按薪资是否大于8000分组情况:" + part);
System.out.println("员工按性别分组情况:" + group);
System.out.println("员工按性别、地区:" + group2);
}
/**
* Collectors提供了一系列用于数据统计的静态方法:
* 计数: count
* 平均值: averagingInt、 averagingLong、 averagingDouble
* 最值: maxBy、 minBy
* 求和: summingInt、 summingLong、 summingDouble
* 统计以上所有: summarizingInt、 summarizingLong、 summarizingDouble
* @author xuqinghai
* @date 2021/11/14 0014 下午 14:19
* @return void
*/
private static void test04(){
//统计员工人数
Long count = personList.stream().collect(Collectors.counting());
//求平均工资
Double average = personList.stream().collect(Collectors.averagingDouble(l->l.getSalary().doubleValue()));
//求最高工资
Optional<BigDecimal> max = personList.stream().map(Person::getSalary).collect(Collectors.maxBy(BigDecimal::compareTo));
//求年龄之和
Integer sum = personList.stream().collect(Collectors.summingInt(Person::getAge));
//求工资之和
Double salarySum = personList.stream().collect(Collectors.summarizingDouble(l->l.getSalary().doubleValue())).getSum();
//一次性统计所有信息
DoubleSummaryStatistics collect = personList.stream().collect(Collectors.summarizingDouble(l->l.getSalary().doubleValue()));
System.out.println("统计员工人数:"+count);
System.out.println("求平均工资:"+average);
System.out.println("求最高工资:"+max);
System.out.println("求工资之和:"+salarySum);
System.out.println("求年龄之和:"+sum);
System.out.println("一次性统计所有信息:"+collect);
}
private static void test03() {
Map<String, Person> collect = personList.stream().filter(x -> x.getAge() > 21)
.collect(Collectors.toMap(Person::getName, y -> y));
System.out.println(collect);
}
private static void test02() {
List<String> list = Arrays.asList("aaa","bbb","ccc","ddd","eee","fff","ggg");
List<String> result = list.stream().map(x->{return x.substring(0,1).toUpperCase()+x.substring(1);})
.collect(Collectors.toList());
System.out.println(list);
System.out.println("====================================================");
System.out.println(result);
}
private static void test01() {
List<String> arr = new ArrayList<String>(){{
add("11");
add("22");
add("33");
add("44");
add("55");
add("66");
add("77");
add("88");
add("99");
add("00");
}
};
List<String> result = arr.stream().map(x->{if(Integer.valueOf(x)%2 == 0){
x = "xxxx";
System.out.println(x);
} return x;}).collect(Collectors.toList());
System.out.println(result);
System.out.println("=======================");
System.out.println(arr);
}
}
复制代码
划线
评论
复制
发布于: 4 小时前阅读数: 4
Geek_4bdbe1
关注
还未添加个人签名 2020.09.21 加入
还未添加个人简介
评论