JavaSE-Java8的两个重要特性
jdk8 新特性
函数式接口:
函数式接口是什么?如果接口中只声明有一个抽象方法,则此接口成为函数式接口(FunctionalInterface)
为什么要有函数式接口?因为只有给函数式接口创建对象时,才可以使用lambda表达式。
java8中声明的函数式接口所在包:java.util.function
4个基本的函数式接口:(直接copy宋的课件)
函数式接口 | 称谓 | 参数类型 | 用途 |
---|---|---|---|
Consumer<T> |
消费型接口 | T | 对类型为T的对象应用操作,包含方法: void accept(T t) |
Supplier<T> |
供给型接口 | 无 | 返回类型为T的对象,包含方法:T get() |
Function<T, R> |
函数型接口 | T | 对类型为T的对象应用操作,并返回结果。结果是R类型的对象。包含方法:R apply(T t) |
Predicate<T> |
判断型接口 | T | 确定类型为T的对象是否满足某约束,并返回 boolean 值。包含方法:boolean test(T t) |
lambda表达式
lambda表达式怎么用?
语法规则:
->的左边:lambda的形参列表,参数的类型都可以省略。如果形参列表只有一个,则一对()也可以省略。
->的右边:lambda体,只有一行执行语句时,则一对{}可以省略,如果有return,则也要省略。
写法举例
1 | Comparator<Integer> com = (o1 , o2) -> Integer.compara(o1,o2); |
lambda表达式的本质:
一方面,lambda表达式作为接口实现类的对象;另一方面,lambda表达式是匿名函数。
方法引用
-
方法引用可以看作是lambda表达式的进一步刻画。
-
当需要提供一个函数式接口的实例时,我们可以使用lambda表达式提供此实例。
- 当满足一定的条件是,我们还可以使用方法引用或构造器引用替换lambda表达式。
方法引用作为了函数式接口的实例。
格式:
- 对象 :: 实例方法
要求:函数式接口的抽象方法a与其内部实现时调用的对象的某个方法b的形参列表和返回值类型都相同。此时可以考虑使用方法b实现对a的替换、覆盖。
注意此方法b是非静态方法,需要对象调用。 - 类 :: 静态方法
要求:函数式接口的抽象方法a与其内部实现时调用的对象的某个静态方法b的形参列表和返回值类型都相同。此时可以考虑使用方法b实现对a的替换、覆盖。
注意此方法b是静态方法,需要类调用。 - 类 :: 实例方法
要求:函数式接口中的抽象方法a与其内部实现时调用的对象的某个方法b的形参列表和返回值类型都相同。同时,抽象方法a中有n个参数,方法b中有n-1个参数,且抽象方法a的第一个参数作为方法b的调用者,且抽象方法a的后n-1个参数与方法b的n-1个参数的类型相同(或一致)。
注意此方法b是非静态方法,需要对象调用。但是形式上,写出对象a所属的类。
构造器引用
格式:类名 :: new
调用了类名对应的类中某一个确定的构造器。具体调用的是类中的哪一个构造器,取决于函数式接口的抽象方法的形参列表。
数组引用
格式:数组名 :: new
StreamAPI
Stream使用的流程
- 实例化
- 一系列的中间操作
- 执行终止操作
实例化:
三种方法:
方法一:通过集合
例如:对于List结构,直接使用list.stream()
就能创建stream实例
方法二:通过数组
类似方法一,使用Arrays的静态方法stream()Arrays.stream(arr)
方法三:streamof
public static<T> Stream<T> of(T... values)
: 返回一个流
例如:
1 | Stream<Integer> stream = Stream.of(1,2,3,4,5); |
中间操作:
筛选与切片
1 |
|
映射
1 |
|
排序
1 |
|
终止操作:
匹配与查找
1 |
|
归约
1 |
|
收集
1 |
|
JavaSE学习先到这里,中间跳了集合源码、网络编程、反射的内容,之后的考试是真的有点多(光电你罪该万死,数电、单片机、量子力学、热统都让我一个学期考还一堆实验课Щ(◣д◢)Щ),后续打算边用边学,保持写代码的习惯。