流 Stream
是 Java 8 API
添加的一个新的抽象 , Stream
使用一种 类似用 SQL 语句从数据库查询数据 的直观方式提供一种对 Java 集合运算 的高阶抽象。
Stream API可以极大提高 Java 程序员的生产力,让程序员写出高效率、干净、简洁的代码
Stream 将要处理的元素集合看作一种流, 流在管道中传输, 并且可以在管道的节点上进行处理, 比如筛选, 排序,聚合等。
(1)串行流 —— stream
(2)并行流 —— parallelStream
(3)示例
public static void main(String[] args) {
// 创建一个字符集合
List<String> list = Arrays.asList(new String[]{"wanqing", "learns", "Java", ""});
// 生成流
// 方法 1 —— 创建串行流
// 下面的代码实现 过滤出 list 中的空字符串,并且将结果转换为 list
List<String> filtered = list.stream()
.filter(string -> !string.isEmpty())
.collect(Collectors.toList());
System.out.println(filtered.size());
// 方法 2 —— 创建并行流
List<String> filtered2 = list.parallelStream()
.filter(string -> !string.isEmpty())
.collect(Collectors.toList());
}
映射每个元素到对应的结果
示例1:
// 创建一个字符集合
List<String> list = Arrays.asList(new String[]{"wanqing", "learns", "Java", ""});
// 下面的代码实现将 list 集合中所有字符串 string 映射(改变)为 string + string
List<String> reduce = list.stream().map(string -> string + string).collect(Collectors.toList());
// 测试输出 [wanqingwanqing, learnslearns, JavaJava, ]
System.out.println(reduce);
示例2:
求取存放学生类的集合的所有学生年龄和
public class UseOfStream {
public static void main(String[] args) {
List<Student> list1 = new ArrayList<>();
Student s1 = new Student(1, "a");
Student s2 = new Student(2, "a");
list1.add(s1);
list1.add(s2);
// 通过 mapToInt 将学生对象映射为 学生年龄age ,然后再使用 sum 求和 —— 注意:集合为空时这么使用会爆异常,要进行处理
int sum2 = list1.stream().mapToInt(student->student.getAge()).sum();
int max2 = list1.stream().mapToInt(student->student.getAge()).max().getAsInt();
System.out.println("年龄和为:" + sum2);
System.out.println("最大年龄:" + max2);
}
private static class Student{
int age;
String name;
public Student(int age, String name) {
this.age = age;
this.name = name;
}
public int getAge() {
return age;
}
public void setAge(int age) {
this.age = age;
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
}
}
通过设置的条件过滤出元素
// 创建一个字符集合
List<String> list = Arrays.asList(new String[]{"wanqing", "learns", "Java", ""});
// 下面的代码实现 过滤出 list 中的空字符串,并且将结果转换为 list
List<String> filtered = list.stream()
.filter(string -> !string.isEmpty())
.collect(Collectors.toList());
用于对流进行排序,可以通过传入比较器自定义排序规则,也可以使用默认排序规则
关于比较器的内容请看:Java 比较器介绍
List<String> sort = list.stream().sorted(new Comparator<String>() {
@Override
public int compare(String o1, String o2) {
// 自定义排序规则,这里用作示例
return 0;
}
}).collect(Collectors.toList());
使用产生统计结果的收集器对集合数据进行统计
// 四、统计数据的使用
List<Integer> listNums = Arrays.asList(new Integer[]{3, 7, 9, 2, 8});
// 对 int 类型数据进行统计 - 得到整型统计类型类
IntSummaryStatistics statistics = listNums.stream().mapToInt(num ->num).summaryStatistics();
// 得到统计的各个结果
int max = statistics.getMax();
int min = statistics.getMin();
long sum = statistics.getSum();
double average = statistics.getAverage();
reduce
是 Stream
的一个聚合方法,它把一个 Stream
的所有元素按照聚合函数聚合成一个结果
示例1:
单参数的 reduce 使用
reduce(T 操作的基本数据类型,即泛型:: 操作名称)
// reduce 的使用
int max = listNums.stream().reduce(Integer:: max).orElse(-1);
int sum = listNums.stream().reduce(Integer::sum).orElse(0);
示例2:
使用 reduce 对 map 映射后的数据进行处理
public class UseOfStream {
public static void main(String[] args) {
List<Student> list1 = new ArrayList<>();
Student s1 = new Student(1, "a");
Student s2 = new Student(2, "a");
list1.add(s1);
list1.add(s2);
int sum3 = list1.stream().mapToInt(student->student.getAge()).reduce(Integer::sum).orElse(0);
System.out.println("年龄和为:" + sum3);
}
}