赞
踩
JDK8发布已经有很长的一段时间了,以前就简单了解就没继续了解,今天抽空整理了一下,欢迎更正补充。JDK8新特新之一:
Lambda(λ) -- 官网
Lamda实际上就是一个匿名方法, 实例:
@Test public void oldRunable() { new Thread(new Runnable() { @Override public void run() { System.out.println("The old runable now is using!"); } }).start(); }
Lambda表达式:
@Test public void runable() { new Thread(() -> System.out.println("It's a lambda function!")).start(); }
Lambda的类型叫做“目标类型(Target Type)”,它的目标是“函数接口(Functional Interface)”,这是JDK8引入的概念。它的定义是:一个接口,如果只有一个显式声明的抽象方法,那么他就是一个函数接口,一般用@FunctionalInterface标注出来(也可以不标)。示例:
- @FunctionalInterface
- public interface Runnable { void run(); }
- public interface Callable<V> { V call() throws Exception; }
- public interface ActionListener { void actionPerformed(ActionEvent e); }
- public interface Comparator<T> { int compare(T o1, T o2); boolean equals(Object obj); }
注意上面Comparator接口虽然声明了2个接口,但他就是函数接口。这是因为equals方法时Object的,所有的接口都会声明Object的public方法(隐式)的,所以它还是一个函数接口。
Lambda表达式分为了三个方面来阐述,官方地址:
方法引用,示例:
先建一个实体类:
class Person{ @Getter Integer age; @Getter String name; @Getter String firstName; Person(Integer age){ this.age = age; } Person(Integer age, String name){ this.age = age; this.name = name; } Person(String name, String firstName, Integer age){ this.name = name; this.firstName = firstName; this.age = age; } public static int compare(Person a, Person b){ return a.getAge().compareTo(b.getAge()); } }
示例:
- @Test
- public void test(){
- // list 排序
- ArrayList<Person> list = new ArrayList<>();
- list.add(new Person(30));
- list.add(new Person(40));
- list.add(new Person(10));
- System.out.println(list);
-
- list.forEach(a->{System.out.println(a.getAge());});
- // list.sort((a,b)-> b.getAge().compareTo(a.getAge())); // 方法引用
- list.sort(Comparator.comparing(Person::getAge)); // 对象方法引用
- System.out.println(list);
-
- // 数组排序
- Person[] people = new Person[]{
- new Person("name1", "f1", 20),
- new Person("name2", "u2",30),
- new Person("name3", "p3",10),
- new Person("name4R", "r4",60),
- };
- for(Person p : people){
- System.out.println(p.getAge());
- }
- System.out.println(" -- ");
- // 方法一
- // Arrays.sort(people, (a,b)-> a.getAge().compareTo(b.getAge())); // 方法引用
- // 方法二
- // Arrays.sort(people, (a, b) -> Person.compare(a,b)); // 对象方法引用
- // 方法三
- // Arrays.sort(people, Person::compare); // 静态对象方法引用(对象方法必须为静态)
- // for(Person p : people){
- // System.out.println(p.getAge());
- // }
-
- Arrays.sort(people, Comparator.comparing(Person::getFirstName)); // 对象方法引用
- for (Person p: people){
- System.out.println(p.getFirstName());
- }
-
- }
![](https://csdnimg.cn/release/blogv2/dist/pc/img/newCodeMoreWhite.png)
官方文档还写了一种构造器方法引用,示例:
public class LambdaTest {
// 构造器引用
public static
<T, SOURCE extends Collection<T>, DEST extends Collection<T>> DEST transfer(
SOURCE source, Supplier<DEST> collectionFactory
){
DEST result = collectionFactory.get();
for (T t : source) {
result.add(t);
}
return result;
}
@Test
public void test1(){
ArrayList<Person> list = new ArrayList<>();
list.add(new Person(40)); list.add(new Person(10)); System.out.println(list); list.forEach(a->{System.out.println(a.getAge());}); Set<Person> personSet = transfer(list, ()->new HashSet<>()); System.out.println(personSet); // 构造器引用转换-方法引用 personSet = transfer(list, HashSet::new); System.out.println(personSet); // 构造器引用转换-静态引用 list.add(new Person(99)); // 检验对象是否变化 personSet = transfer(list, HashSet<Person>::new); System.out.println(personSet); // 构造器引用转换-泛型静态引用 }
}
另外附加一个lambda对象的创建方式:
new HashSet(); == HashSet::new == HashSet<Person>::new
默认方法引用,有两种方式:
详情请查看官网文档。
流的使用
Java8为集合类引入了另一个重要概念:流(stream)。一个流通常以一个集合类实例为其数据源,然后在其上定义各种操作。流的API设计使用了管道(pipelines)模式。对流的一次操作会返回另一个流。如同IO的API或者StringBuffer的append方法那样,从而多个不同的操作可以在一个语句里串起来。示例:
@Test
public void test2(){
// list 排序
ArrayList<Person> list = new ArrayList<>();
list.add(new Person("name1", "f1", 20));
list.add(new Person("name2", "u2",30));
list.add(new Person("name3", "p3",10));
list.add(new Person("name4R", "r4",60));
System.out.println(list);
list.forEach(a->{System.out.println(a.getAge());});
// 流的使用
List newL = list.stream().filter(a -> a.getFirstName().equals("test1")).distinct().collect(Collectors.toList());
System.out.println(newL);
newL = list.stream().map(a -> Integer.valueOf(a.getAge())).filter(a -> a>20).collect(Collectors.toList());
System.out.println(newL);
newL.forEach(a->{System.out.println(a);});
}
个人流的使用小结:
.stream 转化为流的方式, 用法:list.stream
.map 遍历,用法:.map(m -> new Integer(m))
.filter
拦截器,用法:.filter(a -> a.getA == a)
.forEach
遍历,forEachordered较之比较稳定,顺序执行, 用法: .forEach(a -> System.out.println(a);)
.distinct
去重, 用法:list.stream.distinct()
.collect
收集结果, 用法: .collect(Collectors.toList());
.toArray
转化成数组
.reduce
返回单个结果值(执行层,每次处理一个元素创建一个新值),用法:.reduce(a)
.sorted
排序
.findFirst
查询第一个元素并输出
.findAny
返回任何一个元素,并返回Optional实例
.flatmap
将包含通过映射函数替换源流的每个元素而获得的元素,并使结果平坦化
.limit
限制最大数量值
.max 获取最大值,min反之
.peek
中间操作流,返回一个新流
.skip
从开始的流对象中跳过给定数量的元素
.allMatch
全匹配,匹配成功返回true。同理有anyMatch,noneMatch
.count
计数
Copyright © 2003-2013 www.wpsshop.cn 版权所有,并保留所有权利。