Java stream 结合业务 常用方法总结

背景

前几天公司接了一个大屏展示项目,多个维度数据共用了一张宽表,不同维度只是对数据做了不同得处理。为了减少数据库压力(不用数据库做计算),充分利用cpu资源,决定使用stream对数据处理。于是根据业务总结了以下常用stream操作,并封装成了工具类。

详情

一、List>根据字段求和
1.单字段求和

    /**
     * @param flowList	
     * @param sumBy
     * @return
     */
    public static int flowSum(List> flowList, String sumBy) {
        return flowList.stream().mapToInt(
        obj -> MapUtils.getInteger(obj, sumBy, 0)).sum();
    }

2.相乘并求和

   /**
     * intData*doubleData 求和
     *
     * @param flowList
     * @param doubleData
     * @param intData
     * @return
     */
    public static double flowMulti(List> flowList,
     String doubleData, String intData) {
        return flowList.stream().mapToDouble(obj ->
                MapUtils.getDouble(obj, doubleData, 0.0) * 
                MapUtils.getInteger(obj, intData, 0)).sum();
    }

二、List>过滤并求和
1.单条件过滤并求和

    /**
     * @param flowList
     * @param sumBy
     * @return
     */
    public static int flowFilterSum(List> flowList, String sumBy,
     String filterBy, int filterCondition) {
        if (CollectionUtils.isEmpty(flowList)) {
            return 0;
        }
        return flowList.stream().filter(obj -> {
            return MapUtils.getInteger(obj, filterBy) == filterCondition;
        }).mapToInt(obj -> MapUtils.getInteger(obj, sumBy, 0)).sum();
    }

2.过滤并求和——升级版(多个条件得过滤求和)

    /**
     * 多个条件得过滤求和
     *
     * @param flowList
     * @param sumBy
     * @return
     */
    public static int flowFilterSum(List> flowList, String sumBy, 
    String[] filterBy,int[] filterCondition) {
        return flowList.stream().filter(obj -> {
            boolean flag = true;
            for (int i = 0; i < filterBy.length; i++) {
                flag = flag & (MapUtils.getInteger(obj, filterBy[i]) == filterCondition[i]);
            }
            return flag;
        }).mapToInt(obj -> MapUtils.getInteger(obj, sumBy, 0)).sum();
    }

三、List>过滤
1.单条件过滤

  /**
     * 过滤
     *
     * @param flowList
     * @return
     */
    public static List> flowFilter(List> flowList, 
    String filterBy, int filterCondition) {

        return flowList.stream().filter(e -> MapUtils.getInteger(e, filterBy) 
        == filterCondition).collect(Collectors.toList());
    }

2.两个字段相等过滤

    /**
     * 过滤出filterBy=filterByPlus
     *
     * @param flowList
     * @param filterBy
     * @param filterByPlus
     * @return
     */
    public static List> flowFilterPlus(
    List> flowList, String filterBy, String filterByPlus) {
        return flowList.stream().filter(e -> MapUtils.getInteger(e, filterBy)
         == MapUtils.getInteger(e, filterByPlus)).collect(Collectors.toList());
    }

3.过滤

    /**
     * @param flowList
     * @param equal     (==condition)
     * @param unequal   (!=condition)
     * @param condition
     * @return
     */
    public static List> flowFilter(List> flowList,
     String equal, String unequal, int condition) {
        return flowList.stream().filter(e -> MapUtils.getInteger(e, equal) == condition
                && MapUtils.getInteger(e, unequal) != condition)
                .collect(Collectors.toList());
    }

四、List> 分组求和
1.分组求和

   /**
     * 分组
     *
     * @param flowList
     * @param groupBy  分组字段
     * @param sumBy    求和字段
     * @return
     */
    public static Map flowGroupSum(List> flowList, 
    String groupBy, String sumBy) {
        Map analysis =
                flowList.stream().collect(Collectors.groupingBy(obj ->
                                MapUtils.getInteger((Map) obj, groupBy)
                        , Collectors.summingLong(obj ->
                         MapUtils.getInteger((Map) obj, sumBy, 0))));
        return analysis;
    }

2.多条件分组求和

    public static Map flowGroup(List> flowList,
     String sumBy, String... groupBy) {
        Map analysis =
                flowList.stream().collect(Collectors.groupingBy(obj ->
                        {
                            StringBuffer buffer = new StringBuffer();
                            for (int i = 0; i < groupBy.length; i++) {
                                if (i == groupBy.length - 1) {
                                    buffer.append(MapUtils.getString(obj, groupBy[i]));
                                } else {
                                    buffer.append(MapUtils.getString(obj, groupBy[i]) + ":");
                                }
                            }
                            return buffer.toString();
                        }
                        , Collectors.summingLong(obj ->
                         MapUtils.getInteger((Map) obj, sumBy, 0))));
        return analysis;
    }

3.分组过滤求和

    /**
     * @param flowList
     * @param groupBy
     * @param sumBy
     * @param filterBy        过滤字段
     * @param filterCondition 过滤值
     * @return
     */
    public static Map flowFilterGroup(List> flowList, 
    String groupBy, String sumBy,String filterBy, int filterCondition) {
        // 区县数据分组
        Map analysis = flowList.stream().filter(obj -> {
            return MapUtils.getInteger(obj, filterBy) == filterCondition;
        }).collect(Collectors.groupingBy(obj -> MapUtils.getInteger((Map) obj, groupBy)
                , Collectors.summingLong(obj -> MapUtils.getInteger((Map) obj, sumBy, 0))));
        return analysis;
    }

五、List>去重
Map得key是根据params通过分隔符【:】拼接起来,确定数据得唯一
1.多条件去重

   /**
     * 去重
     *
     * @param flowList
     * @param groupBy
     * @return
     */
    public static Set distinct(List> flowList, 
    String... groupBy) {
        Set distinctSet = flowList.stream().map(obj -> {
            StringBuffer buffer = new StringBuffer();
            for (int i = 0; i < groupBy.length; i++) {
                if (i == groupBy.length - 1) {
                    buffer.append(MapUtils.getString(obj, groupBy[i]));
                } else {
                    buffer.append(MapUtils.getString(obj, groupBy[i]) + ":");
                }
            }
            return buffer.toString();
        }).collect(Collectors.toSet());
        return distinctSet;
    }

六、Map 转List>
Map得key是根据params通过分隔符【:】拼接起来得,此方法用于上一个方法去重后,格式化数据返回给前端。

    /**
     * map组装成list返回
     *
     * @param flowMap
     * @param params
     * @return
     */
    public static List> mapTransList(Map flowMap,
     String... params) {
        List> returnList = flowMap.entrySet().stream().map(obj -> {
            String[] temp = obj.getKey().split(":");
            Map tempMap = new HashMap<>();
            for (int i = 0; i < params.length; i++) {
                tempMap.put(params[i], temp[i]);
            }
            return tempMap;
        }).collect(Collectors.toList());
        return returnList;
    }

七、Set转List>

    /**
     * 分割set成list
     *
     * @param set
     * @param groupBy
     * @return
     */
    public static List> split(Set set, String... groupBy) {
        List> list = set.stream().map(obj -> {
            String[] temp = obj.split(":");
            Map tempMap = new HashMap<>();
            for (int i = 0; i < temp.length; i++) {
                tempMap.put(groupBy[i], temp[i]);
            }
            return tempMap;
        }).collect(Collectors.toList());
        return list;
    }

八、分组List–>Map

	list.stream().collect(Collectors.groupingBy(Obj::getProvinceId
                , Collectors.mapping(Obj::getCityId, Collectors.toList())));

九、计算百分比
没有用到stream,但由于大屏业务常用,因此记录下来

    /**
     * @param groupMap
     * @param df
     * @param index
     * @return
     */
    public static Map computerPer(Map groupMap, 
    int total, DecimalFormat df, int index) {
        Map returnMap = new HashMap<>();
        double countPer = 0.0;
        // 保留两位小数
        for (int i = 1; i <= index; i++) {
            // 确保百分比之和为100
            if (i == index) {
                returnMap.put(i, Double.parseDouble(df.format(100 - countPer)));
            } else {
                double per = Double.parseDouble(df.format(groupMap.get(i) * 100.0 / total));
                countPer += per;
                returnMap.put(i, per);
            }
        }
        return returnMap;
    }

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