基础知识点-(Java 8特性)Lambda表达式

为什么引入Lambda表达式

在Java中传递一个代码段不容易,不能直接传递代码段。Java是一种面向对象语言,必须构造一个对象,这个对象的类需要有一个方法能包含所需的代码。

Lambda表达式是一个可传递对的代码块,可以在以后执行一次或多次。

Lambda表达式的语法

(parameters)->expression或(parameters)->{statements}

以下是Lambda表达式的重要特征:

  • 可选类型说明:不需要声明参数类型,编译器可以统一识别参数值。
  • 可选的参数圆括号:一个参数无需定义圆括号,但多个参数需要定义圆括号(如果没有参数,需要有圆括号)。
  • 可选的大括号:如果主体包含了一个语句,就不需要大括号。
  • 可选的返回关键字:如果主体只有一个表达式返回值则编译器会自动返回值,大括号需要指定明表达式返回一个数值。

函数式接口

对于只有一个抽象方法的接口,需要这种接口的对象时,就可以提供一个lambda表达式,这种接口称为函数式接口。

为什么函数接口必须要有一个抽象方法呢?是因为接口完全有可能重新声明Object类的方法,这些声明有可能让方法不再是抽象的。

       在java 8中已经为我们定义了很多常用的函数式接口它们都放在java.util.function包下面,一般有以下常用的四大核心接口:

函数式接口参数类型返回类型用途
Consumer<T>(消费型接口)Tvoid对类型为T的对象应用操作。void accept(T t)
Supplier<T>(供给型接口)T返回类型为T的对象。 T get();
Function<T, R>(函数型接口)TR对类型为T的对象应用操作并返回R类型的对象。R apply(T t);
Predicate<T>(断言型接口)Tboolean确定类型为T的对象是否满足约束。boolean test(T t);

在任意函数式接口上使用@FuctionalInterface注解,这样可以检测它是否是一个函数式接口,同时javadoc会包含一条声明,说明这个接口是一个函数式接口。

方法引用

要用::操作符分隔方法名与对象或类名。主要有三种情况:

  • object::instanceMethod  对象::实例方法名
  • Class::staticMethod    类名::静态方法名
  • Class::instanceMethod  类名::实例方法名

前两种情况中,方法引用等价于提供方法参数的Lambda表达式。Math::pow等价于(x,y)->Math.pow(x,y)。

第三种情况,第1个参数会成为方法的目标。例如,String::compareToIngoreCose等价于(x,y)->x.compareToIngoreCase(y)。

可以在方法引用中使用this参数。例如,this::equals等同于x->this.equals(x)。

使用super也是合法的。super::instanceMethod 使用this做目标,会调用方法的超类版本。

构造器引用

和方法引用类似,方法名为new。采用哪一个构造器,取决于上下文。

可以用数组类型建立构造器引用。例如,int[]::new是一个构造器引用,它有一个参数:即数组的长度。这等价于Lambda表达式x->new int[x]。

变量工作域

lambda表达式有三个部分:

  • 一个代码块
  • 参数
  • 自由变量的值

lambda表达式可以捕获外围作用域的中变量的值。在Java中,要确保捕获的值是明确定义的。在Lambda表达式中,只能引用值不会改变的的变量。

Lambda表达式中捕获的变量必须实际上是最终变量,实际上的最终变量是指,这个变量初始化之后就不会为它赋新值。

Lambda表达式中的体与嵌套块有相同的作用域。在lambda表达式中声明一个与局部变量同名的参数或局部变量是不合法的。

在一个Lambda表达式使用this关键字,是指创建这个Lambda表达式的方法的this参数。

          

 

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值