Lambda 表达式、方法引用(Method Reference)语法

Lambda 表达式

使用Lambda必须先定义一个只有一个抽象类的接口(或者用java、spring boot等内置的接口)

复制代码
// 1. 定义接口
interface MyCommand {
    // 里面只能有一个没写具体代码的方法
    void doWork(); 
}
 // --- 传统写法(比较啰嗦) ---
        MyCommand cmd1 = new MyCommand() {
            @Override
            public void doWork() {
                System.out.println("这是我的自定义任务!");
            }
        };
        cmd1.doWork(); // 调用

        // --- Lambda 写法(超级简单) ---
        MyCommand cmd2 = () -> System.out.println("这是我的自定义任务!");
        cmd2.doWork(); // 调用

1、无参数,无返回值

复制代码
// 传统写法
Runnable r1 = new Runnable() {
    @Override
    public void run() {
        System.out.println("执行任务");
    }
};

// Lambda 写法
Runnable r2 = () -> System.out.println("执行任务");

2、有参数,无返回值

复制代码
// 传统写法
Consumer<String> c1 = new Consumer<String>() {
    @Override
    public void accept(String s) {
        System.out.println(s);
    }
};

// Lambda 写法
Consumer<String> c2 = (s) -> System.out.println(s);

3、单参数可省略括号

复制代码
Consumer<String> c2 = s -> System.out.println(s);

4、有参数、有返回值

复制代码
// 传统写法:要写 5 行代码
MathOperation add = new MathOperation() {
    @Override
    public int operate(int a, int b) {
        return a + b;
    }
};

// Lambda 写法:只要 1 行代码
MathOperation add = (a, b) -> a + b;

Method Reference

表格

Lambda 写法 方法引用简化版 类型说明
(admin) -> admin.getName() admin::getName 对象实例方法引用(引用类的实例方法)
(str) -> System.out.println(str) System.out::println 对象实例方法引用(引用现有对象的实例方法)
(a, b) -> Math.max(a, b) Math::max 静态方法引用(引用类的静态方法)
复制代码
import java.util.function.Function; // Java 自带的"接收者"接口

import java.util.function.Function;

public class Test {
    public static void main(String[] args) {
        User user = new User();
        user.setName("张三");

        // =========================================================
        // 写法 1:传统匿名内部类 (最啰嗦,像写八股文)
        // =========================================================
        Function<User, String> func1 = new Function<User, String>() {
            @Override
            public String apply(User u) {
                return u.getName();
            }
        };
        System.out.println("写法 1 结果:" + func1.apply(user));


        // =========================================================
        // 写法 2:Lambda 表达式 (简化版,去掉了多余的外壳)
        // =========================================================
        // (u) -> u.getName(); 意思是:给我一个 u,返回 u.getName()
        Function<User, String> func2 = (u) -> u.getName();
        System.out.println("写法 2 结果:" + func2.apply(user));


        // =========================================================
        // 写法 3:方法引用 (极致简化,你项目中用的就是这个)
        // =========================================================
        // User::getName 意思是:直接用 User 的 getName 方法
        Function<User, String> func3 = User::getName;
        System.out.println("写法 3 结果:" + func3.apply(user));
    }
}

class User {
    private String name;
    public String getName() { return name; }
    public void setName(String name) { this.name = name; }
}

// 1. 自定义一个接口,规定方法名叫 extract
interface MyDataExtractor {
    String extract(User u); // 注意:这里我故意不叫 apply,叫 extract
}

public class Test {
    public static void main(String[] args) {
        User user = new User();
        user.setName("张三");

        // =========================================================
        // 写法 1:传统写法 (老老实实实现 extract 方法)
        // =========================================================
        MyDataExtractor func1 = new MyDataExtractor() {
            @Override
            public String extract(User u) { // 必须叫 extract
                return u.getName();
            }
        };
        System.out.println("写法 1 结果:" + func1.extract(user));


        // =========================================================
        // 写法 2:Lambda 写法 (自动填入 extract 的坑里)
        // =========================================================
        // 虽然你没写 extract,但 Java 知道这个接口只有一个坑叫 extract
        MyDataExtractor func2 = (u) -> u.getName(); 
        System.out.println("写法 2 结果:" + func2.extract(user)); // 调用时还是用 extract


        // =========================================================
        // 写法 3:方法引用 (自动填入 extract 的坑里)
        // =========================================================
        MyDataExtractor func3 = User::getName;
        System.out.println("写法 3 结果:" + func3.extract(user)); // 调用时还是用 extract
    }
}

class User {
    private String name;
    public String getName() { return name; }
    public void setName(String name) { this.name = name; }
}
相关推荐
Mr-Wanter8 分钟前
Spring Boot 接口签名实践
java·spring boot
denlaku23 分钟前
JDK 22 新特性详解
java·开发语言
余槐i28 分钟前
开虚拟线程后接口反而更慢:JDK 21 synchronized 锁住载体线程的排查
java·spring boot·redis·mysql·性能优化
思码梁田1 小时前
CSS 浏览器厂商前缀:从「写 5 遍」到现代自动化兼容
前端·css·css3·border-radius·1024程序员节·box-shadow·厂商前缀
Sirens.1 小时前
网络通信基础:IP、端口、协议分层与数据封装
java·网络·网络协议·tcp/ip·java-ee·1024程序员节
Bug收容所1 小时前
Vue+JS Day3
前端·javascript·vue.js·前端框架·1024程序员节
CRMEB系统商城1 小时前
服装连锁的导购分销与企微私域
java·大数据·开发语言·人工智能·小程序·php·1024程序员节
iCxhust1 小时前
如何实时同步自己的工作日志,在不同的设备间
前端·软件工程·1024程序员节·同步日志
若亦_1 小时前
Java泛型入门:类型安全与上界约束
java·1024程序员节