已复制
全屏展示
复制代码

Java之lambda表达式总结


· 3 min read

一. 使用方法举例

Java程序中,我们经常遇到一大堆单方法接口,即一个接口只定义了一个方法,此时可以以匿名类方式编写。如下是一个排序的例子

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

public class Main {
    public static void main(String[] args) throws Exception {
        String[] array = {"ccc", "aaa", "bbb"};
        Arrays.sort(array, new Comparator<String>() {
            public int compare(String s1, String s2) {
                return s1.compareTo(s2);
            }
        });
        System.out.println(Arrays.toString(array));
    }
}
  • 如果使用Lambda的方式来编写,可以简化代码如下
import java.util.Arrays;

public class Main {
    public static void main(String[] args) throws Exception {
        String[] array = {"ccc", "aaa", "bbb"};
        Arrays.sort(array, (s1, s2) -> s1.compareTo(s2));
        System.out.println(Arrays.toString(array));
    }
}
  • 如果使用方法引用的方式来编写,可以简化代码如下
import java.util.Arrays;

public class Main {
    public static void main(String[] args) throws Exception {
        String[] array = {"ccc", "aaa", "bbb"};
        Arrays.sort(array, String::compareTo);
        System.out.println(Arrays.toString(array));
    }
}

二. lambda语法详细解释

  • 参数是(s1, s2),参数类型、返回值都可以省略,因为编译器可以自动推断出类型。
  • -> { ... }表示方法体,所有代码写在内部即可。
  • 如果只有一行return xxx的代码,可以简写成(s1, s2) -> s1.compareTo(s2)
(s1, s2) -> {
    return s1.compareTo(s2);
}

// 不需要参数,返回值为 5
() -> 5


// 接收一个参数(数字类型),返回其2倍的值
x -> 2 * x


// 接受2个参数(数字),并返回他们的差值
(x, y) -> x – y


// 接收2个int型整数,返回他们的和
(int x, int y) -> x + y


// 接受一个 string 对象,并在控制台打印,不返回任何值
(String s) -> System.out.print(s)

三. 普通方法引用替代lambda

如下代码在Arrays.sort()中直接传入了静态方法cmp的引用,用Main::cmp表示。因此,所谓方法引用,是指如果某个方法签名和接口恰好一致,就可以直接传入方法引用。因为Comparator<String>接口定义的方法是int compare(String, String),和静态方法int cmp(String, String)相比,除了方法名外,方法参数一致,返回类型相同,因此,我们说两者的方法签名一致,可以直接把方法名作为Lambda表达式传入。所以Arrays.sort(array, Main::cmp);还可以改为Arrays.sort(array, String::compareTo);

import java.util.Arrays;

public class Main {
    public static void main(String[] args) throws Exception {
        String[] array = {"ccc", "aaa", "bbb"};
        Arrays.sort(array, Main::cmp);
        System.out.println(Arrays.toString(array));
    }
    static int cmp(String s1, String s2) {
        return s1.compareTo(s2);
    }
}

四. 构造方法引用替代lambda

除了可以引用静态方法和实例方法,我们还可以引用构造方法。

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

        Person p1 = new Person("name1");
        System.out.println(p1);

        // 匿名类的方式实现实现接口的创建Person的方法
        PersonFactory pf2 = new PersonFactory(){
            @Override
            public Person createPerson(String name) {
                return new Person(name);
            }
        };
        Person p2 = pf2.createPerson("name2");
        System.out.println(p2);

        // 使用lambda的方式实现一个接口,因为要实现的接口只有一个方法
        PersonFactory pf3 = (name) -> new Person(name);
        Person p3 = pf3.createPerson("name3");
        System.out.println(p3);

        // 使用 方法引用 直接引用 Person 的构造方法
        PersonFactory pf4 = Person::new;
        Person p4 = pf4.createPerson("name4");
        System.out.println(p4);


    }
}

interface PersonFactory {
    Person createPerson(String name);
}

class Person {
    String name;

    @Override
    public String toString() {
        return "Person{" +
                "name='" + name + '\'' +
                '}';
    }

    public Person(String name) {
        this.name = name;
    }
}
🔗

文章推荐