JAVA 8: Stream流方法

JAVA 8 Stream流方法


首先创建一个实体类,以及初始化数据

public class Student {
    private String name;
    private int age;
    private int score;
    private String email;
    private String password;

    public Student(String name, int age, int score) {
        this.name = name;
        this.age = age;
        this.score = score;
    }
}
List<Student> studentList = new ArrayList<>(Arrays.asList(
    new Student("小白", 20, 1),
    new Student("小黑", 21, 2),
    new Student("小红", 22, 3),
    new Student("小明", 22, 4),
    new Student("小刚", 22, 5)));

一、filter()

  • 接收一个谓词,返回符合谓词的数据流
List<Student> filter = studentList.stream().filter(x -> x.getAge() > 21).collect(toList());

二、distinct()

  • 流中元素进行去重操作
//去除流中重复元素 (根据流中元素的 hashCode() 和 equals() 方法来实现)
List<Integer> distinct = studentList.stream().map(Student::getAge).distinct().collect(toList());

三、limit()

  • 返回流中前N个元素
List<Student> limit = studentList.stream().limit(2).collect(toList());

四、skip()

  • 跳过前N个元素
List<Student> skip = studentList.stream().skip(2).collect(toList());

skip方法与limit方法配合使用可以实现分页的效果

int pageSize = 2; //每页几条
int pageNum = 2; //第几页
List<Student> limitAndSkip = studentList.stream().skip((pageNum - 1) * pageSize).limit(pageSize).collect(toList());

五、map()

  • 接收一个函数,映射到所有的元素上,返回一个新的流

类似的具体到类型 mapToDouble()、mapToInt()、mapToLong()

List<String> map = studentList.stream().map(Student::getName).collect(toList());

六、flatMap()

  • 扁平化也可以理解为合并流

类似的还有flatMapToDouble、flatMapToInt、flatMapToLong

//这儿将name拆分成数组转换成流,最后将多个name流合并到一起
List<String> flatMap1 = studentList.stream().flatMap(y -> Arrays.stream(y.getName().split(""))).distinct().collect(toList());

//在定义一个List<List<T>>
List<Student> studentList1 = new ArrayList<>(Arrays.asList(
    new Student("小话", 20, 90),
    new Student("小噶", 21, 95),
    new Student("小乐", 22, 80),
    new Student("小嘻", 22, 82)));
List<List<Student>> lists = new ArrayList<>();
lists.add(studentList);
lists.add(studentList1);

//这儿将lists中的list合并成了一个list
List<Student> flatMap2 = lists.stream().flatMap(Collection::stream).collect(toList());

七、anyMatch()、noneMatch()、allMatch()

  • 参数谓词,检验流中至少一个返回为true
// 是否有年龄等于44的数据
boolean anyMatch = studentList.stream().anyMatch(x -> x.getAge() == 44);
// 检查谓词是否不匹配流中所有元素
boolean noneMatch = studentList.stream().noneMatch(x -> x.getAge() == 44);
// 检验流中所有元素是否都为true
boolean allMatch = studentList.stream().allMatch(x -> x.getAge() == 44);

八、reduce()

  • 将流归约为单个值

有三个参数:

​ 1、U identity

​ 初始值

​ 2、BiFunction<U, ? super T, U> accumulator

​ 该函数传入两个参数,返回一个参数,累加器

​ 3、BinaryOperator combiner

​ 组合器,将多个流,应用该函数合并到一起,只有在并行流中生效

//reduce() 一个参数:归约累加 计算所有学生的总成绩
Integer reduce1 = studentList.stream().map(Student::getScore).reduce(Integer::sum).orElse(1);
//reduce 两个参数:设置初始值 然后再相乘
//1*2*3*4*5*10
Integer reduce2 = studentList.stream().map(Student::getScore).reduce(10, (x, y) -> x * y);
//10+1+2+3+4+5
//reduce 两个参数:这儿不是并行流,组合器是无效的,其实就是求和
Integer reduce3 = studentList.stream().map(Student::getScore).reduce(10, Integer::sum, Integer::sum);
//10+1+2+3+4+5  第三个参数,在没有并行流的情况下是无效的,所以结果同上,组合器是相乘但是无效
Integer reduce4 = studentList.stream().map(Student::getScore).reduce(10, Integer::sum, (x, y) -> x * y);

下面介绍在 并行流 中, 组合器 的使用

//并行流reduce,初始值应用在了每个流上然后使用累加器,最后将流合并到一起
// 10+1  10+2  10+3  10+4 10+5 最后将他们全部累加
Integer reduce5 = studentList.stream().map(Student::getScore).parallel().reduce(10, Integer::sum, Integer::sum);

//10*1+10*2+10*3+10*4+10*5
Integer reduce6 = studentList.stream().map(Student::getScore).parallel().reduce(10, (x, y) -> x * y, Integer::sum);

//(10+1)*(10+2)*(10+3)*(10+4)*(10+5)
Integer reduce7 = studentList.stream().map(Student::getScore).parallel().reduce(10, Integer::sum, (x, y) -> x * y);

九、findFirst()、findAny()

  • findFirst()返回第一个
  • findAny()返回随机一个
Student findAny = studentList.stream().findAny().orElse(null);

十、forEach()、forEachOrdered

  • 遍历,参数是一个消费者函数,在单流中没任何区别,在并行流中,forEach无序,forEachOrdered有序
//forEach() 循环
studentList.stream().forEach(x -> x.setAge(20));
//forEach() 按顺序循环
studentList.stream().forEachOrdered(x -> x.setAge(23));

十一、count()

  • 计算流中元素的个数
long count = studentList.stream().count();

十二、max(),min()

  • 流中的最大值,最小值
Student max = studentList.stream().max(Comparator.comparing(Student::getAge)).orElse(null);

十三、sorted

  • 对流中元素按照规则排序

无参或有一个参数

​ 1、Comparator<? super T> comparator

​ 是一个比较器,传入两个参数,返回一个int,形如(x,y)->{}

这儿有两个比较重要的点:

1、返回一个int类型,返回正数或零x与y位置不变,返回负数交换x与y的位置
2、x是流中后面的元素,y是流中前面的元素

//无参,默认按照升序
List<Integer> sorted1 = studentList.stream().map(Student::getScore).sorted().collect(toList());
//传入一个比较器
List<Student> sorted2 = studentList.stream().sorted(Comparator.comparing(Student::getAge)).collect(toList());
//参照上面的知识点y在前面,x在后面,y比x小则交换位置,所以得出结论
//这儿按照年龄倒序
List<Student> sorted3 = studentList.stream().sorted((x, y) -> {
    int xAge = x.getAge();
    int yAge = y.getAge();
    return yAge - xAge;
}).collect(toList());

十四、peek()

  • 接收一个 Consumer 函数作为参数,并将该函数应用到流中每个元素上
//这儿将年龄全都改成23岁
List<Student> peek = studentList.stream().peek(x -> {
    x.setAge(23);
}).collect(toList());

十五、collect()

  • 归约将元素收集到一个容器中

有三个参数:

​ 1、Supplier supplier

​ 供给函数,声明具体的容器

​ 2、BiConsumer<R, ? super T> accumulator

​ 累加器,所有的元素执行该函数

​ 3、BiConsumer<R, R> combiner

​ 组合器,将多个流,应用该函数合并到一起,只有在并行流中生效

List<Integer> intList = new ArrayList<>(Arrays.asList(1, 2, 3, 4, 5));
LinkedList<Object> collectList = intList.parallelStream()
    .collect(LinkedList::new, (list, i) -> {
    System.out.println("【" + i + "】 + 【2】 = 【" + (i + 2) + "】");
    list.add(i + 2);
}, (list1, list2) -> {
    List<Object> cache = new ArrayList<>(list1);
    list1.addAll(list2);
    System.out.println("【" + cache + "】.addAll【" + list2 + "】 = 【"+list1+"】");
});

// 【3】 + 【2】 = 【5】
// 【1】 + 【2】 = 【3】
// 【5】 + 【2】 = 【7】
// 【2】 + 【2】 = 【4】
// 【4】 + 【2】 = 【6】
// 【[3]】.addAll【[4]】 = 【[3, 4]】
// 【[6]】.addAll【[7]】 = 【[6, 7]】
// 【[5]】.addAll【[6, 7]】 = 【[5, 6, 7]】
// 【[3, 4]】.addAll【[5, 6, 7]】 = 【[3, 4, 5, 6, 7]】
System.out.println(collectList); // [3, 4, 5, 6, 7]


十六、parallel()

  • 转换为并行流
System.out.println(studentList.stream().parallel().isParallel()); // true

完整代码

public class StreamTest {
    public static void main(String[] args) {
        List<Student> studentList = new ArrayList<>(Arrays.asList(
                new Student("小白", 20, 1),
                new Student("小黑", 21, 2),
                new Student("小红", 23, 3),
                new Student("小明", 24, 4),
                new Student("小刚", 25, 5)));

        //filter()  过滤获取年龄大于21的学生
        //接收一个谓词 (一个返回 boolean 的函数) 作为参数,返回一个包括所有符合谓词的元素流
        List<Student> filter = studentList.stream().filter(x -> x.getAge() > 21).collect(toList());
        //distinct 去重 年龄去重
        //去除流中重复元素 (根据流中元素的 hashCode() 和 equals() 方法来实现)
        List<Integer> distinct = studentList.stream().map(Student::getAge).distinct().collect(toList());
        //limit  获取前一个数据
        //截断流,返回一个不超过指定长度的流
        List<Student> limit = studentList.stream().limit(1).collect(toList());
        //skip() 跳过前几个数据
        //跳过元素,返回一个跳过了前 n 个元素的流
        List<Student> skip = studentList.stream().skip(2).collect(toList());
        // limit 配合skip可以有高级用法,比如查询分页
        int pageSize = 2; //每页几条
        int pageNum = 2; //第几页
        List<Student> limitAndSkip = studentList.stream().skip((pageNum - 1) * pageSize).limit(pageSize).collect(toList());
        //map() 接收一个函数作为参数,将该函数应用到流中每个元素上,并将其映射成一个新的元素,返回由新元素组成的流
        //将studentList获取name流并转换成集合  类似的 mapToDouble()、mapToInt()、mapToLong()
        List<String> map = studentList.stream().map(Student::getName).collect(toList());

        List<Student> studentList1 = new ArrayList<>(Arrays.asList(
                new Student("小话", 20, 90),
                new Student("小噶", 30, 95),
                new Student("小乐", 40, 80),
                new Student("小嘻", 50, 82)));
        List<List<Student>> lists = new ArrayList<>();
        lists.add(studentList);
        lists.add(studentList1);
        //flatMap 扁平化也可以理解为合并流,这儿就是将Name分段成数组,转换成流合并到一起去重并返回
        //类似的根据类型flatMapToDouble、flatMapToInt、flatMapToLong
        List<String> flatMap1 = studentList.stream().flatMap(y -> Arrays.stream(y.getName().split(""))).distinct().collect(toList());
        //可以将list内的list合并成一个list如下
        List<Student> flatMap2 = lists.stream().flatMap(Collection::stream).collect(toList());
        //anyMatch()  检查谓词是否至少匹配流中一个元素
        boolean anyMatch = studentList.stream().anyMatch(x -> x.getAge() == 44);
        //noneMatch() 检查谓词是否不匹配流中所有元素
        boolean noneMatch = studentList.stream().noneMatch(x -> x.getAge() == 44);
        boolean allMatch = studentList.stream().allMatch(x -> x.getAge() == 44);
        //reduce() 归约累加 计算所有学生的总成绩
        Integer reduce1 = studentList.stream().map(Student::getScore).reduce(Integer::sum).orElse(1);
        //reduce 设置初始值 然后再相加
        //1*2*3*4*5*10
        Integer reduce2 = studentList.stream().map(Student::getScore).reduce(10, (x, y) -> x * y);
        //10+1+2+3+4+5
        Integer reduce3 = studentList.stream().map(Student::getScore).reduce(10, Integer::sum, Integer::sum);
        //10+1+2+3+4+5  第三个参数,在没有并行流的情况下是无效的,所以结果同上
        Integer reduce4 = studentList.stream().map(Student::getScore).reduce(10, Integer::sum, (x, y) -> x * y);
        //10*1+2+3+4+5
        // 10+1  10+2  10+3  10+4 10+5 运行流程并行流,第三个参数可省略,默认使用第二个参数合并流
        Integer reduce5 = studentList.stream().map(Student::getScore).parallel().reduce(10, Integer::sum, Integer::sum);
        //10*1+10*2+10*3+10*4+10*5
        Integer reduce6 = studentList.stream().map(Student::getScore).parallel().reduce(10, (x, y) -> x * y, Integer::sum);
        //(10+1)*(10+2)*(10+3)*(10+4)*(10+5)
        Integer reduce7 = studentList.stream().map(Student::getScore).parallel().reduce(10, Integer::sum, (x, y) -> x * y);
        //findFirst()返回第一个
        //findAny()返回随机一个
        Student findAny = studentList.stream().findAny().orElse(null);
        //forEach() 循环
//        studentList.stream().forEach(x -> x.setAge(20));
        //forEach() 按顺序循环
//        studentList.stream().forEachOrdered(x -> x.setAge(23));
        //count() 获得流中的个数
        long count = studentList.stream().count();
        //max()、 min()
        Student max = studentList.stream().max(Comparator.comparing(Student::getAge)).orElse(null);
        //sorted() 排序
        List<Integer> sorted1 = studentList.stream().map(Student::getScore).sorted().collect(toList());
        List<Student> sorted2 = studentList.stream().sorted(Comparator.comparing(Student::getAge)).collect(toList());
        List<Student> sorted3 = studentList.stream().sorted((x, y) -> {
            int xAge = x.getAge();
            int yAge = y.getAge();
            return yAge - xAge;
        }).collect(toList());
        //peek()  接收一个 Consumer 函数作为参数,并将该函数应用到流中每个元素上
        List<Student> peek = studentList.stream().peek(x -> {
            x.setAge(23);
        }).collect(toList());
        //collect()
        LinkedList<Object> collect = studentList.stream().parallel().collect(LinkedList::new, LinkedList::add, LinkedList::addAll);
        //parallel():并行流
        //isParallel():是否是并行流
        List<Student> parallel = studentList.stream().parallel().collect(toList());
        //close关闭流
        //onClose关闭流时调用该方法
        Stream<Student> onClose = studentList.stream().onClose(() -> System.out.println("哈哈哈哈哈哈哈"));
        onClose.close();
        //iterator() 流的迭代器
        Iterator<Student> iterator = studentList.stream().iterator();
        //sequential() 返回顺序的等效流
        //unordered() 与之相反的,无序的
        studentList.stream().sequential();
        //spliterator()
        Spliterator<Student> spliterator = studentList.stream().spliterator();
        spliterator.forEachRemaining(System.out::println);
        //Stream.of()
        //Stream.empty()
        //Stream.concat()
        //Stream.builder()
        //Stream.iterate()
        //Stream.generate()

        List<Integer> intList = new ArrayList<>(Arrays.asList(1, 2, 3, 4, 5));
        LinkedList<Object> collectList = intList.parallelStream()
                .collect(LinkedList::new, (list, i) -> {
                    System.out.println("【" + i + "】 + 【2】 = 【" + (i + 2) + "】");
                    list.add(i + 2);
                }, (list1, list2) -> {
                    List<Object> cache = new ArrayList<>(list1);
                    list1.addAll(list2);
                    System.out.println("【" + cache + "】.addAll【" + list2 + "】 = 【" + list1 + "】");
                });
    }
}
  • 2
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值