Java8 Stream常用API整理

本文详细介绍Java8中Stream API的使用方法,包括过滤、映射、排序、收集等操作,以及如何结合Lambda表达式提高代码效率和可读性。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

Java8中有两大最为重要的改变,第一个是Lambda表达式,另外一个则是Stream API。

  • 流是Java8引入的全新概念,它用来处理集合中的数据。
  • 众所周知,集合操作非常麻烦,若要对集合进行筛选、投影,需要写大量的代码,而流是以声明的形式操作集合,它就像SQL语句,我们只需告诉流需要对集合进行什么操作,它就会自动进行操作,并将执行结果交给你,无需我们自己手写代码。
  • 在项目中使用Stream API可以大大提高效率以及代码的可读性,使我们对数据进行处理的时候事半功倍。
  • 如果想了解Java8其余的一些特性请看这里,这是我之前整理的Java8特性。
这篇博文以实战角度出发,讲解平时开发中常用API的用法以及一些注意的地方。
  • 首先创建一个对象
public class Employee {

	private int id;
	private String name;
	private int age;
	private double salary;
	private Status status;

	public enum Status {
		FREE, BUSY, VOCATION;
	}

	public Employee() {
	}

	public Employee(String name) {
		this.name = name;
	}

	public Employee(String name, int age) {
		this.name = name;
		this.age = age;
	}
	
	public Employee(int id, String name, int age, double salary) {
		this.id = id;
		this.name = name;
		this.age = age;
		this.salary = salary;
	}

	public Employee(int id, String name, int age, double salary, Status status) {
		this.id = id;
		this.name = name;
		this.age = age;
		this.salary = salary;
		this.status = status;
	}
	//省略get,set等。。。
}
  • 随便初始化一些数据
	List<Employee> empList = Arrays.asList(new Employee(102, "李四", 59, 6666.66, Status.BUSY),
			new Employee(101, "张三", 18, 9999.99, Status.FREE), new Employee(103, "王五", 28, 3333.33, Status.VOCATION),
			new Employee(104, "赵六", 8, 7777.77, Status.BUSY), new Employee(104, "赵六", 8, 7777.77, Status.FREE),
			new Employee(104, "赵六", 8, 7777.77, Status.FREE), new Employee(105, "田七", 38, 5555.55, Status.BUSY));
中间操作
  • 根据条件筛选filter
	/**
	 * 接收Lambda, 从流中排除某些元素。
	 */
	@Test
	void testFilter() {
		empList.stream().filter((e) -> {
			return e.getSalary() >= 5000;
		}).forEach(System.out::println);
	}
  • 跳过流的前n个元素skip
	/**
	 * 跳过元素,返回一个扔掉了前n个元素的流。
	 */
	@Test
	void testSkip() {
		empList.stream().filter((e) -> e.getSalary() >= 5000).skip(2).forEach(System.out::println);
	}
  • 去除重复元素distinct
	/**
	 * 筛选,通过流所生成元素的 hashCode() 和 equals() 去除重复元素
	 */
	@Test
	void testDistinct() {
		empList.stream().distinct().forEach(System.out::println);
	}
  • 截取流的前n个元素limit
	/**
	 * 截断流,使其元素不超过给定数量。
	 */
	@Test
	void testLimit() {
		empList.stream().filter((e) -> {
			return e.getSalary() >= 5000;
		}).limit(3).forEach(System.out::println);
	}
  • 映射map
	/**
	 * 接收一个函数作为参数,该函数会被应用到每个元素上,并将其映射成一个新的元素
	 */
	@Test
	void testMap() {
		empList.stream().map(e -> e.getName()).forEach(System.out::println);

		empList.stream().map(e -> {
			empList.forEach(i -> {
				i.setName(i.getName() + "111");
			});
			return e;
		}).collect(Collectors.toList());
	}
  • 自然排序sorted
	/**
	 * 产生一个新流,其中按自然顺序排序
	 */
	@Test
	void testSorted() {
		empList.stream().map(Employee::getName).sorted().forEach(System.out::println);
	}
  • 自定义排序sorted(Comparator comp)
	/**
	 * 产生一个新流,其中按自然顺序排序
	 */
	@Test
	void testSortedComparator() {
		empList.stream().sorted((x, y) -> {
			if (x.getAge() == y.getAge()) {
				return x.getName().compareTo(y.getName());
			} else {
				return Integer.compare(x.getAge(), y.getAge());
			}
		}).forEach(System.out::println);
	}
最终操作
  • 是否匹配任一元素anyMatch
	/**
	 * 检查是否至少匹配一个元素
	 */
	@Test
	void testAnyMatch() {
		boolean b = empList.stream().anyMatch((e) -> e.getStatus().equals(Status.BUSY));
		System.out.println("boolean is : " + b);
	}
  • 是否匹配所有元素allMatch
	/**
	 * 检查是否匹配所有元素
	 */
	@Test
	void testAllMatch() {
		boolean b = empList.stream().allMatch((e) -> e.getStatus().equals(Status.BUSY));
		System.out.println("boolean is : " + b);
	}
  • 是否未匹配所有元素noneMatch
	/**
	 * 检查是否没有匹配的元素
	 */
	@Test
	void testNoneMatch() {
		boolean b = empList.stream().noneMatch((e) -> e.getStatus().equals(Status.BUSY));
		System.out.println("boolean is : " + b);
	}
  • 返回第一个元素findFirst
	/**
	 * 返回第一个元素
	 */
	@Test
	void testFindFirst() {
		Optional<Employee> op = empList.stream().sorted((e1, e2) -> Double.compare(e1.getSalary(), e2.getSalary()))
				.findFirst();
		if (op.isPresent()) {
			System.out.println("first employee name is : " + op.get().getName().toString());
		}
	}
  • 返回流中任意元素findAny
	/**
	 * 返回当前流中的任意元素
	 */
	@Test
	void testFindAny() {
		Optional<Employee> op = empList.stream().sorted((e1, e2) -> Double.compare(e1.getSalary(), e2.getSalary()))
				.findAny();
		if (op.isPresent()) {
			System.out.println("any employee name is : " + op.get().getName().toString());
		}
	}
  • 返回流的总数count
	/**
	 * 返回流中元素的总个数
	 */
	@Test
	void testCount() {
		long count = empList.stream().filter((e) -> e.getStatus().equals(Status.FREE)).count();
		System.out.println("Count is : " + count);
	}
  • 返回流中的最大值max
	/**
	 * 返回流中最大值
	 */
	@Test
	void testMax() {
		Optional<Double> op = empList.stream().map(Employee::getSalary).max(Double::compare);

		System.out.println(op.get());
	}
  • 返回流中的最小值min
	/**
	 * 返回流中最小值
	 */
	@Test
	void testMin() {
		Optional<Employee> op2 = empList.stream().min((e1, e2) -> Double.compare(e1.getSalary(), e2.getSalary()));

		System.out.println(op2.get());
	}
  • 归约reduce
    归约是将集合中的所有元素经过指定运算,折叠成一个元素输出
	/**
	 * 可以将流中元素反复结合起来,得到一个值。返回T
	 */
	@Test
	void testReduce() {
		Optional<Double> op = empList.stream().map(Employee::getSalary).reduce(Double::sum);

		System.out.println(op.get());
	}

	/**
	 * 可以将流中元素反复结合起来,得到一个值,返回Optional< T>
	 */
	@Test
	void testReduce1() {
		Optional<Integer> sum = empList.stream().map(Employee::getName).flatMap(Java8Stream::filterCharacter)
				.map((ch) -> {
					if (ch.equals('六'))
						return 1;
					else
						return 0;
				}).reduce(Integer::sum);

		System.out.println(sum.get());
	}
  • 将元素收集到list里Collectors.toList()
	/**
	 * 把流中的元素收集到list里。
	 */
	@Test
	void testCollectorsToList() {
		List<String> list = empList.stream().map(Employee::getName).collect(Collectors.toList());

		list.forEach(System.out::println);
	}
  • 将元素收集到set里Collectors.toSet()
	/**
	 * 把流中的元素收集到set里。
	 */
	@Test
	void testCollectorsToSet() {
		Set<String> list = empList.stream().map(Employee::getName).collect(Collectors.toSet());

		list.forEach(System.out::println);
	}
  • 把流中的元素收集到新创建的集合里Collectors.toCollection(HashSet::new)
	/**
	 * 把流中的元素收集到新创建的集合里。
	 */
	@Test
	void testCollectorsToCollection() {
		HashSet<String> hs = empList.stream().map(Employee::getName).collect(Collectors.toCollection(HashSet::new));

		hs.forEach(System.out::println);
	}
  • 根据比较器选择最大值Collectors.maxBy()
	/**
	 * 根据比较器选择最大值。
	 */
	@Test
	void testCollectorsMaxBy() {
		Optional<Double> max = empList.stream().map(Employee::getSalary).collect(Collectors.maxBy(Double::compare));

		System.out.println(max.get());
	}
  • 根据比较器选择最小值Collectors.minBy()
	/**
	 * 根据比较器选择最小值。
	 */
	@Test
	void testCollectorsMinBy() {
		Optional<Double> max = empList.stream().map(Employee::getSalary).collect(Collectors.minBy(Double::compare));

		System.out.println(max.get());
	}
  • 对流中元素的某个字段求和Collectors.summingDouble()
	/**
	 * 对流中元素的整数属性求和。
	 */
	@Test
	void testCollectorsSummingDouble() {
		Double sum = empList.stream().collect(Collectors.summingDouble(Employee::getSalary));

		System.out.println(sum);
	}
  • 对流中元素的某个字段求平均值Collectors.averagingDouble()
	/**
	 * 计算流中元素Integer属性的平均值。
	 */
	@Test
	void testCollectorsAveragingDouble() {
		Double avg = empList.stream().collect(Collectors.averagingDouble(Employee::getSalary));

		System.out.println(avg);
	}
  • 分组,类似sql的group by Collectors.groupingBy
	/**
	 * 分组
	 */
	@Test
	void testCollectorsGroupingBy() {
		Map<Status, List<Employee>> map = empList.stream().collect(Collectors.groupingBy(Employee::getStatus));

		System.out.println(map);
	}
  • 多级分组
	/**
	 * 多级分组
	 */
	@Test
	void testCollectorsGroupingBy1() {
		Map<Status, Map<String, List<Employee>>> map = empList.stream()
				.collect(Collectors.groupingBy(Employee::getStatus, Collectors.groupingBy((e) -> {
					if (e.getAge() >= 60)
						return "老年";
					else if (e.getAge() >= 35)
						return "中年";
					else
						return "成年";
				})));

		System.out.println(map);
	}
  • 字符串拼接Collectors.joining()
	/**
	 * 字符串拼接
	 */
	@Test
	void testCollectorsJoining() {
		String str = empList.stream().map(Employee::getName).collect(Collectors.joining(",", "----", "----"));

		System.out.println(str);
	}
public static Stream<Character> filterCharacter(String str) {

		List<Character> list = new ArrayList<>();
		for (Character ch : str.toCharArray()) {
			list.add(ch);
		}
		return list.stream();
	}
<think>好的,我现在需要帮用户查找Java编程中常用API列表及用法。首先,用户提到了参考中的引用[1]和引用[2],里面提到了ArrayList、Configuration类、FileSystem类等。这说明用户可能对集合类、文件操作相关的API感兴趣。 接下来,我应该先整理Java中最常用API类别,比如集合框架、IO/NIO、多线程、网络编程、数据库连接等。用户示例中的引用涉及集合和Hadoop文件系统,所以可能需要详细说明这些部分。 用户可能需要具体的示例代码,比如如何创建ArrayList,如何使用FileSystem操作HDFS。同时,用户的问题还要求生成相关问题,所以需要预先考虑用户可能进一步询问的方向,比如性能优化、使用场景等。 另外,注意用户提到的系统级指令,比如行内公式用$...$,独立公式用$$...$$,但当前问题可能不涉及数学公式,所以可能不需要处理这部分。但需要确保LaTeX语法正确,如果有变量的话。 用户引用的内容中,引用[1]是ArrayList的初始化示例,引用[2]是关于Hadoop文件系统的操作类,比如Configuration和FileSystem。需要将这些内容自然地融入到回答中,并在引用处添加标识。 可能还需要补充其他常用API,比如String相关的方法,日期时间APIJava 8的Time API),多线程中的ExecutorService,网络编程中的Socket,数据库的JDBC等。每个部分给出简洁的示例,如代码片段,并说明用途。 最后,生成的相关问题需要与Java API相关,可能涉及如何选择集合类、IO和NIO的区别、多线程同步方法、JDBC连接步骤等。确保问题覆盖用户可能感兴趣的后续知识点。</think>### Java常用API列表及用法指南 #### 一、集合框架(核心API) 1. **ArrayList** 基础用法:动态数组实现,支持快速随机访问 ```java ArrayList<String> list = new ArrayList<>(); //初始化[^1] list.add("Java"); //添加元素 String element = list.get(0); //获取元素 ``` 2. **HashMap** 键值对存储结构,时间复杂度$O(1)$ ```java HashMap<Integer, String> map = new HashMap<>(); map.put(1, "API"); String value = map.get(1); ``` #### 二、文件操作API 1. **HDFS文件系统操作**(需hadoop-core依赖) ```java // 读取HDFS文件示例[^2] Configuration conf = new Configuration(); FileSystem fs = FileSystem.get(URI.create("hdfs://hadoop1:9000"), conf); FSDataInputStream in = fs.open(new Path("/input.txt")); ``` 2. **本地文件IO** ```java // 使用Java NIO读取文件 Path path = Paths.get("data.txt"); List<String> lines = Files.readAllLines(path, StandardCharsets.UTF_8); ``` #### 三、多线程API 1. **ExecutorService** 线程池管理工具 ```java ExecutorService executor = Executors.newFixedThreadPool(5); executor.submit(() -> System.out.println("多线程任务")); ``` 2. **synchronized** 同步代码块实现线程安全 ```java public synchronized void criticalSection() { // 线程安全操作 } ``` #### 四、数据库连接(JDBC) ```java // MySQL连接示例 Class.forName("com.mysql.cj.jdbc.Driver"); Connection conn = DriverManager.getConnection( "jdbc:mysql://localhost:3306/test", "user", "pass"); Statement stmt = conn.createStatement(); ResultSet rs = stmt.executeQuery("SELECT * FROM users"); ``` #### 五、新特性APIJava 8+) 1. **Stream API** 函数式数据处理 ```java List<Integer> numbers = Arrays.asList(1,2,3); int sum = numbers.stream().filter(n -> n%2==0).mapToInt(n->n).sum(); ``` 2. **DateTime API** 时间日期处理 ```java LocalDateTime now = LocalDateTime.now(); DateTimeFormatter formatter = DateTimeFormatter.ofPattern("yyyy-MM-dd HH:mm"); ```
评论 4
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值