JAVA8 新特性STREAM的使用

一、简介

             一个list集合,如果我们想根据里面对象的某个字段分组,则需要遍历,然后分组;

             一个list集合,如果我们想根据里面对象的某几个字段分组,求另一个指定字段的和,则需要遍历,然后分组;

             java8提供的stream新特性,都可以以很短的代码来解决这种需求。

二、案例

2.1 情景

           比方说我有一个list集合,里面存储的是User对象,  User对象有三个字段,分别是: 姓名、地区、年龄(还可以多个字段)。

           现有如下需求:  根据名称分组;  根据名称和地区分组; 根据名称分组求对应的年龄总和; 根据名称和地区分组求对应的年龄总和;

2.2 准备

2.2.1 User对象如下:

package com.authorization.privilege;

import java.util.ArrayList;
import java.util.List;
import java.util.LongSummaryStatistics;
import java.util.Map;
import java.util.stream.Collectors;

/**
 * @author qjwyss
 * @date 2019/2/26
 * @description
 */
public class User {

    private String name;
    private String area;
    private Integer age;

    public String getName() {
        return name;
    }

    public void setName(String name) {
        this.name = name;
    }

    public String getArea() {
        return area;
    }

    public void setArea(String area) {
        this.area = area;
    }

    public Integer getAge() {
        return age;
    }

    public void setAge(Integer age) {
        this.age = age;
    }

    public User() {
    }

    public User(String name, String area, Integer age) {
        this.name = name;
        this.area = area;
        this.age = age;
    }

    @Override
    public String toString() {
        return "User{" +
                "name='" + name + '\'' +
                ", area='" + area + '\'' +
                ", age=" + age +
                '}';
    }
}

 2.2.2 初始化数据

public static void main(String[] args) {

        List<User> userList = new ArrayList<>();
        userList.add(new User("zhangsan", "beijing", 10));
        userList.add(new User("zhangsan", "beijing", 20));
        userList.add(new User("lisi", "shanghai", 30));

}

2.3 需求

2.3.1 根据名称分组

// 单个字段分组
Map<String, List<User>> map1 = userList.stream().collect(Collectors.groupingBy(User::getName));
System.out.println(map1);

 结果如下:

 

2.3.2 根据名称和地区分组

// 多个字段分组
Map<String, List<User>> map2 = userList.stream().collect(Collectors.groupingBy(e -> e.getName() + "_" + e.getArea()));
System.out.println(map2);

结果如下:

 

2.3.3 根据名称分组求对应的年龄总和

// 单列求和 比方说:只根据name字段分组求和
int sum = userList.stream().mapToInt(User::getAge).sum();
System.out.println(sum);

结果如下:

2.3.4 根据名称和地区分组求对应的年龄总和

 // 多列求和 比如说:根据name字段和area字段求和
Map<String, List<User>> map3 = userList.stream().collect(Collectors.groupingBy(e -> e.getName() + "_" + e.getArea()));
List<Object> newUserList = map3.keySet().stream().map(key -> {
      User user = new User();
      user.setName(key.split("_")[0]);
      user.setArea(key.split("_")[1]);
      Integer sumAge = 0;
      List<User> eachUserList = map3.get(key);
      for (User eachUser: eachUserList) {
           sumAge += eachUser.getAge();
      }
      user.setAge(sumAge);
      return user;
}).collect(Collectors.toList());
System.out.println(newUserList);

结果如下:

 

 

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值