zoukankan      html  css  js  c++  java
  • Java8中的Stream

    一、Stream简介

    Java 8 中的 Stream 是对集合(Collection)对象功能的增强,它专注于对集合对象进行各种非常便利、高效的聚合操作(aggregate operation),或者大批量数据操作 (bulk data operation)。Stream API 借助于 Lambda 表达式,极大的提高编程效率和程序可读性。同时它提供串行和并行两种模式进行汇聚操作,并发模式能够充分利用多核处理器的优势,使用 fork/join 并行方式来拆分任务和加速处理过程。通常编写并行代码很难而且容易出错, 但使用 Stream API 无需编写一行多线程的代码,就可以很方便地写出高性能的并发程序。所以说,Java 8 中首次出现的 java.util.stream 是一个函数式语言+多核时代综合影响的产物。

    二、流的操作类型

    即可以对一个流做哪些处理;也即如何消费流。

    Intermediate(中间的) :一个流可以后面跟随零个或多个 intermediate 操作。其目的主要是打开流,做出某种程度的数据映射/过滤,然后返回一个新的流,交给下一个操作使用。这类操作都是惰性化的(lazy),就是说,仅仅调用到这类方法,并没有真正开始流的遍历。
    Terminal (最后的):一个流只能有一个 terminal 操作,当这个操作执行后,流就被使用“光”了,无法再被操作。所以这必定是流的最后一个操作。Terminal 操作的执行,才会真正开始流的遍历,并且会生成一个结果,或者一个 side effect。
    在对于一个 Stream 进行多次转换操作 (Intermediate 操作),每次都对 Stream 的每个元素进行转换,而且是执行多次,这样时间复杂度就是 N(转换次数)个 for 循环里把所有操作都做掉的总和吗?其实不是这样的,转换操作都是 lazy 的,多个转换操作只会在 Terminal 操作的时候融合起来,一次循环完成。我们可以这样简单的理解,Stream 里有个操作函数的集合,每次转换操作就是把转换函数放入这个集合中,在 Terminal 操作的时候循环 Stream 对应的集合,然后对每个元素执行所有的函数。

    三、Stream类UML

    四、开发中常用示例

    1:获取某一列的值

    List<SkuNoMappingDTO> skuNoMappingDTOS = productServiceApiClient.checkExistSku(skuNos);
    if (null == skuNoMappingDTOS || skuNoMappingDTOS.isEmpty()) {
        return Collections.emptyList();
    }
    
    Set<Long> skuIds=skuNoMappingDTOS.stream().map(f->f.getId()).collect(Collectors.toSet());
    

    2:字符串转list

    //01
    List<String> orderNos = Arrays.stream(findInvoiceListParam.getOrder_ids().split(","))
            .collect(Collectors.toList());
    
    
    //02
    List<Integer> messageTypes = new ArrayList<>();
    String[] types = findMessageDTO.getType().split(",");
    messageTypes = Arrays.stream(types).map(Integer::valueOf).collect(Collectors.toList());
    

    3:list转另外一个list

    //01
     List<UserInfo> pageList = userInfoService.list(queryWrapper);
    
     List<UserInfoExp> list = pageList.stream().map(e -> JSONUtil. toBean(JSONUtil.toJsonStr(e), UserInfoExp.class)). collect(Collectors.toList());
    
    
    //02
    List<OperateCard> operateCards = operateCard.selectList(new QueryWrapper<OperateCard>().lambda()
            .eq(OperateCard::getUserBaseId, userBaseId));
    if (null != operateCards && operateCards.size() > 0) {
        return operateCards.stream().map(item -> {
            OperateCardDto operateCardDto = new OperateCardDto();
            BeanUtils.copyProperties(item, operateCardDto);
            return operateCardDto;
        }).collect(Collectors.toList());
    } else {
        return null;
    }
    

    4:int[] 转 List

    int[] userIds =new int[]{1,2,3};
    List<Integer> list01 = Arrays.stream(userIds).boxed().collect(Collectors.toList());
    List<Integer> list02 = IntStream.of(userIds).boxed().collect(Collectors.toList());
    

    5:int[] 转 Integer[]

    int[] userIds =new int[]{1,2,3};
    Integer [] integers01=Arrays.stream(userIds).boxed().toArray(Integer[]::new);
    

    6:List 转 Integer[]

    List<Integer> list = new ArrayList<>();
    Integer[] integers2 = list.toArray(new Integer[0]);
    

    7:List 转 int[]

    List<Integer> list = new ArrayList<>();
    
    
    int[] intArray=list.stream().mapToInt(Integer::valueOf).toArray();
    
    

    引用
    1:IBM-Develop:https://developer.ibm.com/zh/articles/j-lo-java8streamapi/

    --

  • 相关阅读:
    hashlib对密码进行加密
    django中model的choices字段
    django在表发生变化后需执行命令
    djangopost请求报错:Forbidden (CSRF token missing or incorrect.)
    阻止浏览器自动填入账号和密码
    django表的models的参数及含义
    django设置静态文件
    Django的admin管理工具设置中文
    径向渐变
    文档对象的获取
  • 原文地址:https://www.cnblogs.com/Naylor/p/13850504.html
Copyright © 2011-2022 走看看