1、循环:forEach

2、统计个数:count 获取数量

3、过滤:filter 得到名字长度为3个字的人

4、取用前几个:limit 获取前3个数据stream.limit(3).forEach(System.out::println);

5、跳过前几个:skip 跳过前两个数据 stream.skip(3).forEach(System.out::println);

6、映射:map map是将值转换到新的流 Stream<Integer> s = stream.map(Integer::parseInt);

7、排序:sorted

8、去重:distinct stream.distinct().forEach(System.out::println);

9、条件匹配:allMatch、anyMatch、noneMatch System.out.println(stream.allMatch(s -> s.length() > 2));

10、查找第一个元素:stream.findFirst().get()

11、获取最大最小值:max、min Optional<Integer> max = Stream.of(5, 3, 6, 1).max((o1, o2) -> o1 - o2);

12、加减乘除:reduce reduce为终端操作,可以对中间操作筛选出来的流数据作出一系列的加减乘除等操作

13、组合:concat stream连接 Stream<String> newStream = Stream.concat(streamA, streamB);

14、并行Stream流创建及使用:

15、parallelStream线程安全问题

16、分组* .collect(Collectors.groupingBy(Student::getScore))

.collect(Collectors.toMap(s -> s.getName(), s -> s)) 不能有重复的K值

17、集合的拷贝

public class JavaStream流_filter_map_collect {
    /**
     * * 1、循环:forEach
       * 2、统计个数:count   获取数量
     * * 3、过滤:filter  得到名字长度为3个字的人
       * 4、取用前几个:limit   获取前3个数据stream.limit(3).forEach(System.out::println);
       * 5、跳过前几个:skip    跳过前两个数据 stream.skip(3).forEach(System.out::println);
     * * 6、映射:map  map是将值转换到新的流   Stream<Integer> s = stream.map(Integer::parseInt);
     * * 7、排序:sorted
       * 8、去重:distinct   stream.distinct().forEach(System.out::println);
       *
       * 9、条件匹配:allMatch、anyMatch、noneMatch      System.out.println(stream.allMatch(s -> s.length() > 2));
     * * 10、查找第一个元素:stream.findFirst().get()
       * 11、获取最大最小值:max、min     Optional<Integer> max = Stream.of(5, 3, 6, 1).max((o1, o2) -> o1 - o2);
       *
     * * 12、加减乘除:reduce  reduce为终端操作,可以对中间操作筛选出来的流数据作出一系列的加减乘除等操作
       * 13、组合:concat  stream连接 Stream<String> newStream = Stream.concat(streamA, streamB);
       * 14、并行Stream流创建及使用:
       * 15、parallelStream线程安全问题
     * * 16、分组* .collect(Collectors.groupingBy(Student::getScore))
     * * .collect(Collectors.toMap(s -> s.getName(), s -> s))  不能有重复的K值
       * 17、集合的拷贝
       *
     * * collect将stream流转化为给到集合 list  set map
     * *
     */
    Stream<String> stream = Stream.of(null,"1111", "222", "333", "44", "55", "55", null);

    /**
     * 1、循环
     */
    @Test
    public void testForeach() {
        stream.forEach(System.out::println);
    }

    /**
     * 2、获取数量
     */
    @Test
    public void testCount() {
        System.out.println(stream.count());
    }

    /**
     * 3、得到名字长度为3个字的人(过滤)
     */
    @Test
    public void testFilter() {
        stream.filter(s -> s.length() == 3).forEach(System.out::println);
    }

    /**
     * 4、获取前3个数据
     */
    @Test
    public void testLimit() {
        stream.limit(3).forEach(System.out::println);
    }

    /**
     * 5、跳过前两个数据
     */
    @Test
    public void testSkip() {
        stream.skip(3).forEach(System.out::println);
    }

    /**
     * 6、映射
     */
    @Test
    public void testMap() {
        Stream<Integer> s = stream.map(Integer::parseInt);
        s.forEach(System.out::println);
    }

    /**
     * 7、排序  要先过滤掉null ,不然会报空指针
     */
    @Test
    public void testSorted() {
        Stream<Integer> s = stream.filter(Objects::nonNull).map(Integer::parseInt);
        s.sorted((i1, i2) -> i2 - i1).forEach(System.out::println);
    }

    /**
     * 8、去重
     */
    @Test
    public void testDistinct() {
        stream.distinct().forEach(System.out::println);
    }

    /**
     * 9、条件匹配 有空指针异常 需要过滤掉
     */
    @Test
    public void testMatch() {
        System.out.println(stream.filter(Objects::nonNull).allMatch(s -> s.length() > 2));
        System.out.println(stream.anyMatch(s -> s.length() > 2));
        System.out.println(stream.noneMatch(s -> s.length() > 2));
    }

    /**
     * 10、查找第一个元素   有空指针异常 需要过滤掉
     */
    @Test
    public void testFind() {
        System.out.println(stream.findFirst().get());
    }

    /**
     * 11、获取最大最小值    有空指针异常 需要过滤掉
     */
    @Test
    public void testMax_Min() {
        // 获取最大值
        // 1, 3, 5, 6
        Optional<Integer> max = Stream.of(5, 3, 6, 1).max((o1, o2) -> o1 - o2);
        System.out.println("最大值: " + max.get());

        // 获取最小值
        // 1, 3, 5, 6
        Optional<Integer> min = Stream.of(5, 3,null, 6, 1).filter(Objects::nonNull).min((o1, o2) -> o1 - o2);
        System.out.println("最小值: " + min.get());

        // 获取最小值
        // 1, 3, 5, 6
        Optional<Integer> min1 = Stream.of(5, 3, 6, 1).filter(Objects::nonNull).min((o1, o2) -> o1 - o2);
        System.out.println("最小值: " + min1.get());
    }

    /**
     *12、 加减乘除:reduce  reduce为终端操作,可以对中间操作筛选出来的流数据作出一系列的加减乘除等操作
     */
    @Test
    public void testReduce() {
        // T reduce(T identity, BinaryOperator<T> accumulator);
        // T identity: 默认值
        // BinaryOperator<T> accumulator: 对数据进行处理的方式
        // reduce如何执行?
        // 第一次, 将默认值赋值给x, 取出集合第一元素赋值给y
        // 第二次, 将上一次返回的结果赋值x, 取出集合第二元素赋值给y
        // 第三次, 将上一次返回的结果赋值x, 取出集合第三元素赋值给y
        // 第四次, 将上一次返回的结果赋值x, 取出集合第四元素赋值给y
        int reduce = Stream.of(4, 5, 3, 9).reduce(0, (x, y) -> {
            System.out.println("x = " + x + ", y = " + y);
            return x + y;
        });
        System.out.println("reduce = " + reduce); // 21

        // 获取最大值
        Integer max = Stream.of(4, 5, 3, 9).reduce(0, (x, y) -> {
            return x > y ? x : y;
        });
        System.out.println("max = " + max);
    }

            public void testMapReduce() {
                // 求出所有年龄的总和
                // 1.得到所有的年龄
                // 2.让年龄相加
                Integer totalAge = Stream.of(
                        new Person("刘德华", 58),
                        new Person("张学友", 56),
                        new Person("郭富城", 54),
                        new Person("黎明", 52))
                        .map((p) -> p.getAge()).reduce(0, Integer::sum);

                System.out.println("totalAge = " + totalAge);


                // 找出最大年龄
                // 1.得到所有的年龄
                // 2.获取最大的年龄
                Integer maxAge = Stream.of(
                        new Person("刘德华", 58),
                        new Person("张学友", 56),
                        new Person("郭富城", 54),
                        new Person("黎明", 52))
                        .map(p -> p.getAge())
                        .reduce(0, Math::max);
                System.out.println("maxAge = " + maxAge);

                // 统计 a 出现的次数
                //                          1    0     0    1    0    1
                Integer count = Stream.of("a", "c", "b", "a", "b", "a")
                        .map(s -> {
                            if (s == "a") {
                                return 1;
                            } else {
                                return 0;
                            }
                        })
                        .reduce(0, Integer::sum);
                System.out.println("count = " + count);

//实际开发中 :如果列表是中没有数据list.size()==0的时候会报错,所以需要将代码修改成如下:
               // BigDecimal sum=list.stream()
                 //       .map(User::getNum1)  //返回num1的列表
                   //     .reduce(BigDecimal.ZERO,BigDecimal::add);  //列表字段求和,默认是从0开始相加
//或者这种 需求需要返回的值为null,那么需要这样
    //currentMonthFeeList.stream().map(HotelDayElectricFeeEntity::getFee).reduce(BigDecimal::add).orElse(null);
            }

            public void testNumericStream() {
                // Integer占用的内存比int多,在Stream流操作中会自动装箱和拆箱
                Stream<Integer> stream = Stream.of(1, 2, 3, 4, 5);
                // 把大于3的打印出来
                // stream.filter(n -> n > 3).forEach(System.out::println);

                // IntStream mapToInt(ToIntFunction<? super T> mapper);
                // IntStream: 内部操作的是int类型的数据,就可以节省内存,减少自动装箱和拆箱

                IntStream intStream = Stream.of(1, 2, 3, 4, 5).mapToInt(Integer::intValue);
                intStream.filter(n -> n > 3).forEach(System.out::println);
            }

    /**
     * 13、stream连接
     */
    @Test
    public void testContact() {
        Stream<String> streamA = Stream.of("张三");
        Stream<String> streamB = Stream.of("李四");

        // 合并成一个流
        Stream<String> newStream = Stream.concat(streamA, streamB);
        // 注意:合并流之后,不能操作之前的流啦.
        // streamA.forEach(System.out::println);

        newStream.forEach(System.out::println);
    }


    /**
     * 16、集合排序,分组
     * .collect(Collectors.groupingBy(Student::getScore))
     * .collect(Collectors.toMap(s -> s.getName(), s -> s))
     *
     * @author ljyang
     * @date 2022-9-20 15:17
     */
    @Test
    public void entitySort() {
        //Student 的 list 集合
        List<Student> studentsList = new Student().getValue();
        //studentsList=new ArrayList<>();
        System.out.println("原始数据:");
        studentsList.forEach(s ->
                System.out.println(s.getName() + " " + s.getScore() + " " + s.getHeight() + " " + s.getCollege() + "" + s.getAddress()));
        //取出用户集合中id是007并且用用户id生成一个新的集合
        List<String> ls1 = studentsList.stream().map(Student::getName).collect(Collectors.toList());
        List<String> ls2 = studentsList.stream().filter(Objects::nonNull).map(Student::getName).collect(Collectors.toList());
        List<String> ls = studentsList.stream().filter(e -> "80".equals(e.getScore())).map(Student::getName).collect(Collectors.toList());
        //分组
        Map<Integer, List<Student>> groupingByMap = studentsList.stream().collect(Collectors.groupingBy(Student::getScore));


        //抽取对象集合中的某个元素组成集合
        List<Integer> workerIds = studentsList.stream().map(Student::getScore).collect(Collectors.toList());

        //抽取对象集合中的某两个元素组成键值对存入Map
        // case0:
        Map<String, Student> workerMap = new HashMap<>();
        studentsList.forEach(worker -> workerMap.put(worker.getName(), worker));
        // case1:
        Map<String, Student> toMap = studentsList.stream().collect(Collectors.toMap(s -> s.getName(), s -> s));

        //按照集合对象的属性分组
        Map<String, List<Student>> collect = studentsList.stream().collect(Collectors.groupingBy(a -> a.getAddress()));
        //遍历Map
        collect.forEach((k, v) -> System.out.println(k + ":" + v));
    }

   /**
    *测试方法调用 之后集合是否跟着变化
    *
    */
    @Test
    public void test调用() {
        List<User> list = new ArrayList<>();
        list.add(new User(15L, "小白", 27, "1QQ",SexEnum.MALE));
        list.add(new User(16L, "红16", 26, "2QQ",SexEnum.MALE));
        list.add(new User(17L, "红17", 27, "2QQ",SexEnum.MALE));
        list.add(new User(18L, "红18", 28, "2QQ",SexEnum.MALE));
        list.add(new User(19L, "红19", 29, "2QQ",SexEnum.MALE));
        System.err.println("对象List = " + JSONObject.toJSONString(list));
//        List<User> userStream = list.stream().filter(apiId -> {
//            // api不存在或未启用
//            if (apiId.getAge() == 27) {
//                return false;
//            } else {
//                return true;
//            }
//        }).collect(Collectors.toList());
        test306(list);

        list.forEach(System.out::println);
    }
    public void test306(List<User> list) {
        list.stream().filter(apiId -> {
            // api不存在或未启用
            if (apiId.getAge()==27) {
                return false;
            }else{
                return true;
            }
        });
    }
    /**
     * 17、集合的拷贝
     */
    public static void main(String[] args) {
        List<User> list = new ArrayList<>();
        list.add(new User(15L, "小白", 23, "1QQ",SexEnum.MALE));
        list.add(new User(16L, "红16", 26, "2QQ",SexEnum.MALE));
        list.add(new User(17L, "红17", 27, "2QQ",SexEnum.MALE));
        list.add(new User(18L, "红18", 28, "2QQ",SexEnum.MALE));
        list.add(new User(19L, "红19", 29, "2QQ",SexEnum.MALE));
        System.err.println("对象List = " + JSONObject.toJSONString(list));
        List<Student> newList = list.stream().map(e -> {
            Student t = new Student();
            BeanUtils.copyProperties(e, t);
            return t;
        }).collect(Collectors.toList());
        System.err.println("拷贝出来的List = " + JSONObject.toJSONString(newList));
        list.get(0).setId(44L);
        System.err.println("修改list集合对象信息之后  = " + JSONObject.toJSONString(list));
        System.err.println("拷贝出来的List = " + JSONObject.toJSONString(newList));


        //复制到新集合中(map迭代出来),改变旧的集合值,新的集合值也会跟着一一起变化,如果不想变化需要使用BeanUtils.clonebean(Object object)
        List<User> newresult = CollectionHelper.newArrayList(list);

    }
}