Lambda表达式讲解

news/2024/7/7 18:41:23 标签: java, 开发语言, lambda

简介:

Lambda表达式的使用场景非常广泛,主要包括函数式编程、集合操作、排序、线程编程、GUI事件处理、数据处理、Web开发等。

函数式编程:Lambda表达式是函数式编程的重要特性,可以用于替代传统的匿名内部类,简化代码,提高可读性。

集合操作:Lambda表达式可以与集合操作方法(如forEach、filter、map、reduce)结合使用,对集合中的元素进行遍历、筛选、映射、聚合等操作。

排序:Lambda表达式可以用于自定义的排序功能,通过传递不同的比较规则实现对集合中元素的排序。

线程编程:Lambda表达式可以用于简化线程编程中的代码,例如使用Lambda表达式创建Runnable对象、使用Lambda表达式实现函数式接口来处理线程任务等。

GUI事件处理:Lambda表达式可以用于简化GUI事件处理代码,例如为按钮、菜单等组件注册事件监听器。

数据处理:Lambda表达式可以用于对大数据集进行处理,如统计、过滤、转换等,其并行处理的能力可以提高数据处理的效率。

Web开发:Lambda表达式可以用于简化Web开发中的重复性代码,例如通过Lambda表达式实现控制器、过滤器、拦截器等。

1) Lambda表达式仅能放入如下代码:预定义使用了 @Functional 注释的函数式接口,自带一个抽象函数的方法,或者SAM(Single Abstract Method 单个抽象方法)类型。这些称为lambda表达式的目标类型,可以用作返回类型,或lambda目标代码的参数。例如,若一个方法接收Runnable、Comparable或者 Callable 接口,都有单个抽象方法,可以传入lambda表达式。类似的,如果一个方法接受声明于 java.util.function 包内的接口,例如 Predicate、Function、Consumer 或 Supplier,那么可以向其传lambda表达式。

2) lambda表达式内可以使用方法引用,仅当该方法不修改lambda表达式提供的参数。本例中的lambda表达式可以换为方法引用,因为这仅是一个参数相同的简单方法调用。

list.forEach(n -> System.out.println(n)); 
list.forEach(System.out::println);  // 使用方法引用

然而,若对参数有任何修改,则不能使用方法引用,而需键入完整地lambda表达式,如下所示:
list.forEach((String s) -> System.out.println("*" + s + "*"));

事实上,可以省略这里的lambda参数的类型声明,编译器可以从列表的类属性推测出来。

3)lambda内部可以使用静态、非静态和局部变量,这称为lambda内的变量捕获。

4)Lambda表达式在Java中又称为闭包或匿名函数,所以如果有同事把它叫闭包的时候,不用惊讶。

5)Lambda方法在编译器内部被翻译成私有方法,并派发 invokedynamic 字节码指令来进行调用。可以使用JDK中的 javap 工具来反编译class文件。使用 javap -p 或 javap -c -v 命令来看一看lambda表达式生成的字节码。大致应该长这样:

private static java.lang.Object lambda$0(java.lang.String);
6)lambda表达式有个限制,那就是只能引用 final 或 final 局部变量,这就是说不能在lambda内部修改定义在域外的变量。

List<Integer> primes = Arrays.asList(new Integer[]{2, 3,5,7});
int factor = 2;
primes.forEach(element -> { factor++; });
Compile time error : "local variables referenced from a lambda expression must be final or effectively final"
//另外,只是访问它而不作修改是可以的,如下所示:
List<Integer> primes = Arrays.asList(new Integer[]{2, 3,5,7});
int factor = 2;
primes.forEach(element -> { System.out.println(factor*element); });

1、Lambda表达式概述

Lambda表达式是JDK1.8之后的一种语法,是一个匿名函数,是对匿名函数的简写形式,我们可以把 Lambda表达式理解为是一段可以传递的代码(将代码像数据一样进行传递),可以写出更简洁、更灵活的代码。作为一种更紧凑的代码风格,使Java的语言表达能力得到了提升;

首先来看一下什么是Lambda表达式:

import java.util.Arrays;
import java.util.Comparator;
import java.util.List;

public class MyTest {
    public static void main(String[] args) {
        Integer[] ints = {98, 243, 35, 13, 57, 243};
        List<Integer> list = Arrays.asList(ints);    
        //之前的排序
        list.sort(new Comparator<Integer>() {
            @Override
            public int compare(Integer o1, Integer o2) {
                return o2-o1;
            }
        });
        System.out.println(list);
        //[243, 243, 98, 57, 35, 13]

        //使用Lambda表达式
        list.sort((o1,o2)->(o1-o2));

        System.out.println(list);
        //[13, 35, 57, 98, 243, 243]
	}
}

通过上面的对比,发现Lambda表达式式书写起来更为简洁;

2、Lambda表达式语法

JDK1.8之后引入的一种语法,他的写法是使用一个->符号,箭头将Lambda表达式分为左右两部分,左边写的是实现的这个接口中的抽象方法中的形参列表,右边就是对抽象方法的处理;

实现的这个接口中的抽象方法中的形参列表 -> 抽象方法的处理

3、具体写法

因为Lambda表达式的核心就是实现的这个接口中的抽象方法中的形参列表 -> 抽象方法的处理,因此根据形参列表与返回值的不同,Lambda表达式的具体写法也不相同;

无返回值有形参的抽象方法

public class MyTest1 {
    public static void main(String[] args) {
        MyInterface myInterface = new MyInterface() {
            @Override
            public void show(int a, int b) {
                System.out.println(a + b);
            }
        };
		myInterface.show(20, 30);//50

        //简写1:方法名可以自己推断出来
        MyInterface myInterface1 = (int a, int b) -> {
            System.out.println(a + b);
        };

        myInterface1.show(20, 40);//60

        //简写2:可以省略形参列表中的形参类型
        MyInterface myInterface2 = (a, b) -> {
            System.out.println(a + b);//70
        };

        myInterface2.show(20, 50);

        //简写3:如果抽象方法中只有一行代码,可以省略方法体的大括号,当然,如果不止一行,就不能省略
        MyInterface myInterface3 = (a, b) -> System.out.println(a + b);
        myInterface3.show(20, 60);//80
	}
}
public interface MyInterface {
    public abstract void show(int a,int b);
}

可以省略方法名,IDEA会帮你自动检测方法名;
可以省略方法中的形参类型;
如果对抽象方法的实现逻辑只有一行,可以省略方法体的大括号,当然如果不止一行,就不能省略了;

有返回值的抽象方法

public class MyTest2 {
    public static void main(String[] args) {
        MyInterface1 test1 = new MyInterface1() {
            @Override
            public int test(int a, int b) {
                return a - b;
            }
        };
        System.out.println(test1.test(90, 8));//82
        //简写1:
        MyInterface1 test2 = (int a, int b) -> {
            return a - b;
        };
        System.out.println(test2.test(20, 10));//10

        //简写2:
        MyInterface1 test3 = (a, b) -> {return a - b;};
        System.out.println(test3.test(30, 10));//20

        //简写3:这个有返回值的方法,不能直接去掉大括号,还需要去掉return关键字
        MyInterface1 test4 = (a, b) -> a - b;
        System.out.println(test4.test(40, 10));//30
    }
}
public interface MyInterface1 {
    public abstract int test(int a,int b);
}

有返回值的方法,如果要去掉大括号,还需要去掉return关键字;

有一个形参的抽象方法

public class MyTest3 {
    public static void main(String[] args) {
      

http://www.niftyadmin.cn/n/5534907.html

相关文章

web平台—apache

web平台—apache 1. 学apache前需要知道的知识点2. apache详解2.1 概述2.2 工作模式2.3 启动apache网站整体流程2.4 相关文件保存位置2.5 配置文件详解 3. apache配置实验实验1&#xff1a;设置apache的目录别名实验2&#xff1a;apache的用户认证实验3&#xff1a;虚拟主机 (重…

SpringCloud Gateway 网关获取或修改接口响应数据

文章目录 前言一、获取响应数据并打印 前言 我们的网关在之前只记录了接口请求日志&#xff0c;响应日志是没有做记录的&#xff0c;在后续别人对接我们开放平台时出现了一些问题没法确认当时的一个数值状态&#xff0c;照成了很多不必要的麻烦&#xff0c;后来决定在网关添加上…

Flutter——最详细(Badge)使用教程

背景 主要常用于组件叠加上圆点提示&#xff1b; 使用场景&#xff0c;消息数量提示&#xff0c;消息红点提示 属性作用backgroundColor红点背景色smallSize设置红点大小isLabelVisible是否显示offset设置红点位置alignment设置红点位置child设置底部组件 代码块 class Badge…

复分析——第8章——共形映射(E.M. Stein R. Shakarchi)

第8章 共形映射(Conformal Mappings) The results I found for polygons can be extended under very general assumptions. I have undertaken this research because it is a step towards a deeper understanding of the mapping problem, for which not much has hap…

鸿蒙登录页面及页面跳转的设计

目录 任务目标任务分析任务实施1.新建工程项目HMLogin2.设计登录页面Index.visual3.设计第二个页面SecondPage4.修改Index.ets代码5.修改SecondPage.ets代码6.运行工程 任务目标 设计一个简单的登录页面&#xff0c;要求可以将第一页的登录信息&#xff0c;传递到第二个页面&a…

办公软件WPS与Office的区别

临近计算机考试很多同学在纠结我是报wps好&#xff1f;还是ms office好&#xff1f;下面就来详细说说。 1、wps属于国内金山公司的办公软件&#xff0c;里面包含word、Excel和PPT。考试是2021年开始的&#xff01; 2、MS&#xff08;Microsoft 微软&#xff09; office属于美…

【pytorch13】激活函数及梯度

什么是激活函数 计算机科学家借鉴生物的神经元机制发明了计算机上的模型&#xff0c;这个模型与生物的神经元非常类似 激活的意思就是z变量要大于0&#xff0c;这一个节点才会激活&#xff0c;否则就会处于睡眠状态不会输出电平值 该激活函数在z0处不可导&#xff0c;因此不能…

STM32工业自动化控制系统教程

目录 引言环境准备工业自动化控制系统基础代码实现&#xff1a;实现工业自动化控制系统 4.1 数据采集模块 4.2 数据处理与分析 4.3 控制系统实现 4.4 用户界面与数据可视化应用场景&#xff1a;工业自动化与优化问题解决方案与优化收尾与总结 1. 引言 工业自动化控制系统利用…