java函数式接口和Lambda表达式

函数式接口

一种编程范式,主要关注处理数据的函数

函数式接口是指有且仅有一个抽象方法的接口,可以使用@Functionallnterface注解进行标识,函数式接口可以用Lambda表达式来实现,从而简化代码的编写

java 复制代码
@Functionallnterface
interface 接口名{
	唯一的抽象方法
}
函数式接口的注意事项

1,函数式接口的准确定义为有且有且仅有一个抽象方法需要重写

在接口中添加Object类中的方法作为抽象方法,子类可以不重写

Lambda表达式介绍

jdk8引入

只能操作函数式接口
当需要一个函数式接口的实现类对象时使用

1,概述

Lambda表达式由三个部分组成,参数列表,箭头符号和方法体

(parameters)-> {方法体}

Lambda的完全形式

java 复制代码
(T 参数1,T 参数2) -> {语句1;
			 语句2;}

参数列表:包含在括号中,可以省略参数类型

即函数式接口中唯一抽象方法的参数

箭头符号:由"->"组成,将参数和方法体分开

方法体:可以是表达式或者语句块

即函数式接口唯一抽象方法的重写形式
Lambda表达式的应用场景:

1,使用Lambda表达式可以简化匿名内部类的使用

2,可以作为方法参数传递,用于简化回调函数的编写

3,可以用于集合的遍历和筛选操作,简化代码-->Stream流体现

Lambda表达式代码实现:

1,无参无返回值情况
java 复制代码
 @FunctionalInterface
2 interface NoParamNoReturn {
3 	void execute();
4 }
	
// ⽆参⽆返回值的情况
27 public static void executeNoParamNoReturn(NoParamNoReturn func) {
28 func.execute();
29 }

在executeNoParamNoReturn()方法中传入一个NoParamNoReturn接口类型的参数,需要传入一个接口类型的实现类对象,

在之前,我们通常使用匿名内部类进行传入,但是当这个接口中有且仅有一个需要重写的抽象方法时,即这个接口为函数式接口时

我们可以使用Lambda表达式进行简化

java 复制代码
public static void main(String[] args) {
        executeNoParamNoReturn(()->{
            System.out.println("已传递");
        });
    }

调用方法,传入lambda表达式,因为没有参数列表,所以在小括号中无需传入参数,在方法体中因为没有返回值,所以不需要return语句.

传递完接口实现类对象,方法内执行接口实现类对象重写的execute()方法,即输出"已传递".

再来看看其他情况

2,有参有返回值情况
java 复制代码
@FunctionalInterface
interface WithParamWithReturn {
    int add(int a, int b);
}

//有参有返回值的情况
public static int executeWithParamWithReturn(WithParamWithReturn func, int a, int b) {
        return func.add(a, b);
}

public static void main(String[] args) {
        System.out.println(executeWithParamWithReturn((int c,int d)->{
            System.out.println(1);
            return c+d;},1,2));
 }

在测试方法中我们调用executeWithParamWithReturn()方法,可以看到需要传入三个参数:

一个WithParamWithReturn接口类型的实现类对象,

一个int类型的 a

一个int类型的 b

在main方法中我们在需要实现类对象的位置传入lambda表达式

java 复制代码
(int c,int d)->{
    		System.out.println(1);
            return c+d;
}

因为接口内的抽象方法要求传入两个int类型的参数,所以我们相对的也需要传入两个int类型的参数

即小括号内的c 和 d

又因为抽象方法要求一个int类型的返回值,所以我们相对的也需要在返回语句中return一个int类型的值

即return c+d

在方法体中我们又自由发挥了一行语句,输出了一个1


分析到此结束,我们来看一下执行流程

首先在main方法中调用executeWithParamWithReturn()方法,传入WithParamWithReturn类型参数,

即lambda表达式

再传入int类型参数1和2

执行executeWithParamWithReturn()中的方法体

java 复制代码
return func.add(a, b);

返回了接口实现类对象重写的方法的返回值

而我们重写的方法的方法体如下所示

java 复制代码
System.out.println(1);
            return c+d;

在输出1的同时,返回了c+d,也就是参数列表中的a+b,也就是3

再返回给方法调用者executeWithParamWithReturn(),再返回给其调用者主方法

java 复制代码
public static void main(String[] args) {
        System.out.println(executeWithParamWithReturn((int c,int d)->{
            System.out.println(1);
            return c+d;},1,2));
 }

在主方法中我们将返回值打印

所以最后控制台的结果如下

3,lambda表达式的简化

lambda表达式的简化

参数列表中的类型可以省略

参数列表中如果只有一个参数可以省略小括号

方法体中如果只有一句语句可以省略大括号和分号

如果这行代码是return语句,return必须省略

先写一个完整的lambda表达式

java 复制代码
@FunctionalInterface
interface Test {
    int test(int a);
}

public static void main(String[] args) {
     Test test = (int a)->{return a+1;};
     System.out.println(test.test(1));
}

在省略参数类型,参数括号和方法体括号和分号以及return后我们得到

java 复制代码
public static void main(String[] args) {
     Test test = a->a+1;
     System.out.println(test.test(1));
}

有一种热兵器暴打原始人的感觉...

总结:

lambda表达式是一种语法糖,极大的简化了对接口进行创建实现类对象的操作,在接口为函数式接口的前提下完全替代了匿名内部类,使代码显得更加简洁精练.

相关推荐
飞Link2 分钟前
告别盲目找Bug:深度解析 TSTD 异常检测中的预测模型(Python 实战版)
开发语言·python·算法·bug
1.14(java)9 分钟前
Spring-boot快速上手
java·开发语言·javaee
Darkdreams29 分钟前
SpringBoot项目集成ONLYOFFICE
java·spring boot·后端
记忆多39 分钟前
c++名字空间 函数模版 左右值
开发语言·c++·算法
lhbian1 小时前
【Spring Cloud Alibaba】基于Spring Boot 3.x 搭建教程
java·spring boot·后端
2401_889884662 小时前
高性能计算通信库
开发语言·c++·算法
代码雕刻家2 小时前
3.6.Maven-依赖管理-依赖范围
java·maven
范什么特西2 小时前
狂神报错页面设置
java·tomcat
架构师沉默2 小时前
AI 真的会取代程序员吗?
java·后端·架构
Memory_荒年3 小时前
ReentrantLock 线程安全揭秘:从“锁”到“重入”的魔法
java·后端·源码