Java中的Stream流

目录

一、Stream流的概述

1、什么是Stream流?

2、Stream流的实现步骤

3、案例:体验Stream流的作用

3.1、需求

3.2、实现步骤

3.3、不使用stream流的代码

3.4、结果体现

3.5、使用stream流的代码

3.6、结果体现

二、Stream流的获取

1、集合获取Stream流的方式?

2、数组获取Stream流的方式?

三、Stream流的常用方法

1、Stream流的常用非终结操作方法

2、Stream流的常见终结操作方法

四、Stream流的综合应用

1、需求

2、分析

3、代码

4、结果

五、收集Stream流


一、Stream流的概述

1、什么是Stream流?

答:在Java 8中,得益于Lambda所带来的函数式编程, 引入了一个全新的Stream流概念。

目的:用于简化集合和数组操作的API。

2、Stream流的实现步骤

第一步:先得到集合或者数组的Stream流(就是一根传送带)

第二步:把元素放上去

第三步:然后就用这个Stream流简化的API来方便的操作元素。

3、案例:体验Stream流的作用

3.1、需求

按照下面的要求完成集合的创建和遍历

3.2、实现步骤

第一步:创建一个集合,存储多个字符串元素。

Java中的Stream流_第1张图片

第二步:把集合中所有以"张"开头的元素存储到一个新的集合

第三步:把"张"开头的集合中的长度为3的元素存储到一个新的集合

第四步:遍历上一步得到的集合中的元素输出。

3.3、不使用stream流的代码


public class StreamTest {
    public static void main(String[] args) {
        List names = new ArrayList<>();
        Collections.addAll(names,"张三分","张无忌","张强","赵名","周芷若");
        System.out.println(names);

        //1、从集合中找出姓张的放到新集合
        List zhanglist = new ArrayList<>();
        for (String name : names) {
            if (name.startsWith("张")){
                zhanglist.add(name);
            }
        }
        System.out.println(zhanglist);

        //2、找名称长度是3的姓名
        List zhangThreeList = new ArrayList<>();
        for (String s : zhanglist) {
            if (s.length() == 3){
                zhangThreeList.add(s);
            }
        }
        System.out.println(zhangThreeList);
    }
}

3.4、结果体现

3.5、使用stream流的代码

public class StreamTest {
    public static void main(String[] args) {
        List names = new ArrayList<>();
        Collections.addAll(names,"张三分","张无忌","张强","赵名","周芷若");
        System.out.println(names);
        //names.stream().filter(s -> s.startsWith("张")).filter(s -> s.length() == 3).forEach(s -> System.out.println(s));
        names.stream().filter(s -> s.startsWith("张") && s.length() == 3).forEach(s -> System.out.println(s));
    }
}

3.6、结果体现

 

二、Stream流的获取

1、集合获取Stream流的方式?

答:可以使用Collection接口中的默认方法stream​()生成流。

名称

说明

default Stream stream​()

获取当前集合对象的Stream流

代码:

 /**--------------------------Collectio集合获取Stream流---------------*/
        Collection list = new ArrayList<>();
        Stream s = list.stream();

        /**--------------------------Map集合获取Stream流---------------*/
        Map map =new HashMap<>();
        //键流
        Stream keyStream = map.keySet().stream();
        //值流
        Stream valuesStream = map.values().stream();
        //键值对(拿整体)
        Stream> keyAndValueStream = map.entrySet().stream();

 

2、数组获取Stream流的方式?

名称

说明

public static  Stream stream(T[] array)

获取当前数组的Stream流

public static Stream of(T... values) 

获取当前数组/可变数据的Stream流

代码:

/**--------------------------数组获取Stream流---------------*/
        String[] names = {"张无忌", "小花", "小王"};
        Stream ss = Arrays.stream(names);
        Stream ss1 = Stream.of(names);

三、Stream流的常用方法

1、Stream流的常用非终结操作方法

常见方法:

名称

说明

Stream filter(Predicate predicate)

用于对流中的数据进行过滤。

Stream limit​(long maxSize)

获取前几个元素

Stream skip​(long n)

跳过前几个元素

Stream distinct​()

去除流中重复的元素。依赖(hashCode和equals方法)

static  Stream concat​(Stream a, Stream b)

合并a和b两个流为一个流

注意: 

中间方法也称为非终结方法,调用完成后返回新的Stream流可以继续使用,支持链式编程。

在Stream流中无法直接修改集合、数组中的数据。

2、Stream流的常见终结操作方法

常见方法:

名称

说明

void forEach​(Consumer action)

对此流的每个元素执行遍历操作

long count​()

返回此流中的元素数

注意:终结操作方法,调用完成后流就无法继续使用了,原因是不会返回Stream了。 

四、Stream流的综合应用

1、需求

某个公司的开发部门,分为开发一部和二部,现在需要进行年中数据结算。

2、分析

2.1:员工信息至少包含了(名称、性别、工资、奖金、处罚记录)

2.2:开发一部有4个员工、开发二部有5名员工

2.3:分别筛选出2个部门的最高工资的员工信息,封装成优秀员工对象Topperformer

2.4:分别统计出2个部门的平均月收入,要求去掉最高和最低工资。

2.5:统计2个开发部门整体的平均工资,去掉最低和最高工资的平均值。

3、代码

public class StreamDemo04 {

    public static double allmoney1 = 0;
    public static double allmoney2 = 0;
    public static double allmoney3 = 0;

    public static void main(String[] args) {
        List one = new ArrayList<>();
        one.add(new Employee("猪八戒", '男', 30000, 25000, null));
        one.add(new Employee("孙悟空", '男', 25000, 1000, "顶撞上司" ));
        one.add(new Employee("沙僧", '男', 20000, 20000, null));
        one.add(new Employee("小白龙", '男', 20000, 25000, null));

        List two = new ArrayList<>();
        two.add(new Employee("武松", '男', 15000, 9000, null));
        two.add(new Employee("李逵", '男', 20000, 10000, null ));
        two.add(new Employee("西门庆", '男', 50000, 100000, "被打"));
        two.add(new Employee("潘金莲", '女', 3500, 1000, "被打"));
        two.add(new Employee("武大郎", '男', 20000, 0, "下毒"));

        //1、开发一部,最高工资的员工
        //指定大小规则
//        Employee e = one.stream().max((e1,e2) -> Double.compare(e1.getSalary() + e1.getBonus(), e2.getSalary() + e2.getBonus()))
//                .get();
//        System.out.println(e);

        Topperformer t = one.stream().max((e1,e2) -> Double.compare(e1.getSalary() + e1.getBonus(), e2.getSalary() + e2.getBonus()))
                .map(e -> new Topperformer(e.getName(), e.getSalary() + e.getBonus())).get();
        System.out.println(t);

        //2、统计平均工资,去掉最高工资和最低工资(开发一部)
        one.stream().sorted((e1,e2) -> Double.compare(e1.getSalary() + e1.getBonus(), e2.getSalary() + e2.getBonus()))
                .skip(1).limit(one.size() - 2).forEach(e -> {
                    //求出总和:剩余员工的工资总和
                    allmoney1 += (e.getSalary() + e.getBonus());
                });
        System.out.println("开发一部的平均工资为:"+allmoney1/(one.size()-2));


        //3、统计平均工资,去掉最高工资和最低工资(开发二部)
        two.stream().sorted((e1,e2) -> Double.compare(e1.getSalary() + e1.getBonus(), e2.getSalary() + e2.getBonus()))
                .skip(1).limit(two.size() - 2).forEach(e -> {
                    //求出总和:剩余员工的工资总和
                    allmoney2 += (e.getSalary() + e.getBonus());
                });
        //BigDecimal
        BigDecimal b1 = BigDecimal.valueOf(allmoney2);
        BigDecimal b2 = BigDecimal.valueOf(two.size()-2);
        System.out.println("开发二部的平均工资为:"+b1.divide(b2,2, RoundingMode.HALF_UP));



        //4、统计平均工资,去掉最高工资和最低工资(开发二部和开发一部)
        Stream s1 = one.stream();
        Stream s2 = two.stream();
        Stream s3 = Stream.concat(s1,s2);

        s3.sorted((e1,e2) -> Double.compare(e1.getSalary() + e1.getBonus(), e2.getSalary() + e2.getBonus()))
                .skip(1).limit(one.size() + two.size() - 2).forEach(e -> {
                    //求出总和:剩余员工的工资总和
                    allmoney3 += (e.getSalary() + e.getBonus());
                });
        //BigDecimal
        BigDecimal b3 = BigDecimal.valueOf(allmoney3);
        BigDecimal b4 = BigDecimal.valueOf(one.size() + two.size()-2);
        System.out.println("开发一部和开发二部的平均工资为:"+b3.divide(b4,2, RoundingMode.HALF_UP));


    }
}

4、结果

Java中的Stream流_第2张图片

 

五、收集Stream流

1、收集Stream流的含义:就是把Stream流操作后的结果数据转回到集合或者数组中去。

2、Stream流:方便操作集合/数组的手段。

3、集合/数组:才是开发中的目的。

4、Stream流的收集方法

名称

说明

R collect​(Collector collector)

开始收集Stream流,指定收集器

5、 Collectors工具类提供了具体的收集方式

名称

说明

public static  Collector toList​()

把元素收集到List集合中

public static  Collector toSet​()

把元素收集到Set集合中

public static  Collector toMap​(Function keyMapper , Function valueMapper)

把元素收集到Map集合中

6、代码

public static void main(String[] args) {
        List list1 = new ArrayList<>();
        list1.add("张无忌");
        list1.add("周芷若");
        list1.add("赵明");
        list1.add("张强");
        list1.add("张三风");
        list1.add("张三风");


        //收集List集合
        Stream s1 = list1.stream().filter(s -> s.startsWith("张"));
        List zhanglist = s1.collect(Collectors.toList()); //可变集合
        zhanglist.add("Java1");
        System.out.println(zhanglist);

//        List list2 = s1.toList();  //得到不可变集合
//        list2.add("Java");
//        System.out.println(list1);

        //注意:流只能使用一次
        //收集Set集合
        Stream s2 = list1.stream().filter(s -> s.startsWith("张"));
        Set zhanglist1 = s2.collect(Collectors.toSet());
        System.out.println(zhanglist1);

        Stream s3 = list1.stream().filter(s -> s.startsWith("张"));
//        Object[] objects = s3.toArray();
        String[] s = s3.toArray(String[]::new);//定义一个字符串类型的数组
        System.out.println(Arrays.toString(s));
    }

 7、结果展示

 

你可能感兴趣的:(Java,java,开发语言)