Java新特性之Lambda表达式学习

Lambda表达式使用

1、举例
Comparator<Integer> compara2 = (num1, num2) -> Integer.compare(num1, num2);
2、格式

​ ‘->’ 符号是lambda操作符,又叫箭头操作符

​ -> 左边:lambda的形参列表(实际就是接口中抽象方法的形参列表)

​ ->右边:lambda体(实际是重写的抽象方法的方法体)

3、lambda表达式的使用
1)无参无返回值
    Runnable r1 = () -> {
        System.out.println("Hello World");
    };
 (2)一个参数,没有返回值
    // accpet是Consumer接口的抽象方法
    Consumer<String> comsumer1 = (String str) -> {
        System.out.println(str);
    };
	comsumer1.accept("重写Consumer接口的抽象方法");
 (3)数据类型可以省略,因为可以由编译器推断得出,称为“类型推断”,List<String> list = new ArrayList<>();相似
    Consumer<String> consumer3 = (str) -> {
        System.out.println(str);
    };
    consumer3.accept("类型推断Consumer接口的泛型");
 (4)Lambda表达式只有一个参数时,形参的小括号可以省略
    Consumer<String> consumer = str -> {
        System.out.println(str);
    };
	consumer.accept("只有一个参数可以省略括号");
 (5)Lambda需要两个以上的参数,多条执行语句,并且有返回值
    Comparator<Integer> comparator = new Comparator<Integer>() {
        @Override
        public int compare(Integer n1, Integer n2) {
            Integer sum = sum(n1, n2);
            System.out.println(sum);
			Integer sub = sub(n1, n2);
            System.out.println(sub);
            return n1.compareTo(n2);
        }
    };
    int compare = comparator.compare(100, 50);
    System.out.println(compare);

	// lambda写法
	Comparator<Integer> comparator1 = (Integer n1, Integer n2) -> {
        Integer sum = sum(n1, n2);
        System.out.println(sum);
        Integer sub = sub(n1, n2);
        System.out.println(sub);
        return n1.compareTo(n2);
    };
 (6)当lambda体只有一条语句时,return与大括号若有,都可以省略
    Comparator<Integer> comparator = (n1, n2) -> n1.compareTo(n2);
	或者
	Consumer<String> comsumer = str -> System.out.println(str)
    
4、Lambda表达式本质

​ 作为函数式接口的实例

如果有且仅有一个抽象方法的接口,则此接口就称为函数式接口; 函数式接口就是可 以适用于Lambda使用的接口 ,意味着如果需要使用lambda表达式,就必须是函数式接口,所以以前用匿名实现类表示的现在都可以用Lambda表达式来写

例如:

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-FG77kCUY-1653841549056)(C:\Users\信仰斌\AppData\Roaming\Typora\typora-user-images\1653750291334.png)]

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-WRaEomRN-1653841549058)(C:\Users\信仰斌\AppData\Roaming\Typora\typora-user-images\1653750308850.png)]

总结

​ ‘->’lambda符号左侧形参列表类型可以省略(类型推断), 如果lambda形参列表只有一个参数,其()也可以删除;

​ '->'lambda符号右侧的lambda体应该使用一对{}包裹,如果lambda体类只有一条执行语句,则可以省略return和{}(return和{}需要同时省略)

函数式接口

Consumer:消费型接口,内有抽象方法—void accept(T t)
Supplier:生产型接口(供给型),内有抽象方法—T get();
Function<T, R>:函数型接口,内有抽象方法—R apply(T t)
Predicate:断言型接口,内有抽象方法—boolean test(T t)

函数式接口

Consumer例子

public void testConsumer() {
    // 消费型接口Consumer    void accept(T t)
    happyTime(new BigDecimal(500), new Consumer<BigDecimal>() {
        @Override
        public void accept(BigDecimal bigDecimal) {
            System.out.println("花费了" + bigDecimal + "元");
        }
    });

    // lambda写法
    happyTime(new BigDecimal(500), money -> {
        System.out.println("花费了" + money + "元");
    });
	}

    public void happyTime(BigDecimal money, Consumer<BigDecimal> consumer) {
        consumer.accept(money);
    }

Predicate例子

public List<String> testPredicate() {
        // 断言型接口    boolean test(T t)
        List<String> stringList = Arrays.asList("北京", "南京", "天津", "上海", "东京", "西京", "普京");
        List<String> filterString = filterString(stringList, new Predicate<String>() {
            @Override
            public boolean test(String str) {
                return str.contains("京");
            }
        });

        filterString = filterString(stringList, (str) -> {
            return str.contains("京");
        });
        return filterString;
    }

    /**
     * 根据给定的规则过滤集合中的字符串,此规则由实现Predicate的抽象方法决定
     *
     * @param stringList
     * @param predicate
     * @return
     */
    public List<String> filterString(List<String> stringList, Predicate<String> predicate) {
        List<String> filterString = new ArrayList<>();
        for (String str : stringList) {
            if (predicate.test(str)) {
                filterString.add(str);
            }
        }

        return filterString;
    }

方法引用

方法引用的使用

  • 1.使用情景:当要传递给Lambda体的操作,已经有实现的方法了,可以使用方法引用

  • 2.方法引用,本质上是Lambda表达式,而Lambda表达式作为函数式接口的实例,所以方法引用,也是函数式接口的实例

  • 3.使用格式: 类(或对象):: 方法名

  • 4.具体使用分为三种情况:

    • 对象::非静态方法

    • 类::静态方法

    • 类::非静态方法

  • 5.方法引用的要求,要求接口中的抽象方法的形参列表和返回值类型与方法引用的方法的形参列表和返回值类型相同

情况一:对象::实例方法
// Consumer中的void accept(T t)
// PrintStream中的void println(T t)
PrintStream printStream = System.out;
    Consumer<String> consumer1 = printStream::println;
    consumer1.accept("方法引用");
/**
 * Supplier的T get()
 * Employee中的String getName()
 */
public void test2() {
        System.out.println("===lambda表达式====");
        Employee employee = new Employee(1001, "马化腾", 34, 60000);
        Supplier<String> supplier = () -> {
            return employee.getName();
        };
        supplier = () -> employee.getName();
        System.out.println(supplier.get());

        System.out.println("===方法引用===");
        Supplier<String> supplier2 = employee::getName;
        System.out.println(supplier2.get());
    }
情况二:类::静态方法
/**
 * 情况二:类::静态方法
 * Comparator中的int compare(T t1, T t2)
 * Integer中的int compare(T t1, T t2)
 */
public void test3() {
    // lambda表达式
    Comparator<Integer> comparator = (t1, t2) -> {
        return Integer.compare(t1, t2);
    };
    comparator = (t1, t2) -> Integer.compare(t1, t2);
    int compare = comparator.compare(100, 20);
    System.out.println(compare);

    // 方法引用
    Comparator<Integer> comparator1 = Integer::compare;
    int compare1 = comparator1.compare(100, 20);
    System.out.println(compare1);
}

// 有参有返回值
// Function中的R apply(T t)
// Math中的Long round(Double d)
public void test4() {
    // lambda表达式写法
    Function<Double, Long> function = (d) -> {
        return Math.round(d);
    };
    function = d -> Math.round(d);
    System.out.println(function.apply(1.9));

    // 方法引用
    Function<Double, Long> function1 = Math::round;
    System.out.println(function1.apply(1.9));
}
情况三:类::实例方法
// 情况三:类::实例方法
// Comparator中的int compare(T t1, T t2)
// String中的int t1.compareTo(T t2)
public void test5() {
    // Lambda表达式
    Comparator<String> comparator = (s1, s2) -> s1.compareTo(s2);
    int compare = comparator.compare("abc", "abd");
    System.out.println(compare);

    // 方法引用
    Comparator<String> comparator1 = String::compareTo;
    int compare1 = comparator1.compare("abc", "abd");
    System.out.println(compare1);
}

/**
 * BiPredicate中的boolean test(T t1, T t2)
 * Stirng中的boolean t1.equals(t2)
 */
public void test6() {
    // lambda表达式
    BiPredicate<String, String> predicate = (str1, str2) -> str1.equals(str2);
    boolean result = predicate.test("aaa", "222");
    System.out.println(result);

    // 方法引用
    BiPredicate<String, String> predicate1 = String::equals;
    result = predicate1.test("aaa", "222");
    System.out.println(result);
}

// Function中的R apply(T t)
// Employee中的String getName()
public void test7() {
    // Lambda表达式
    Function<Employee, String> function = employee -> employee.getName();
    String name = function.apply(new Employee(1001, "马化腾", 34, 60000));
    System.out.println(name);

    // 方法引用
    Function<Employee, String> function1 = Employee::getName;
    name = function1.apply(new Employee(1001, "mayun", 34, 60000));
    System.out.println(name);
}
构造器引用

​ 和方法引用类似

// 构造器引用
public void test1() {
    // lambda表达式
    Supplier<Employee> supplier = () -> new Employee();

    // 构造器引用
    Supplier<Employee> supplier1 = Employee::new;
    // 调用Supplier接口的抽象方法get()
    Employee employee = supplier1.get();
    System.out.println(employee);
}

// Function中的R apply(T t)
public void test2() {
    // Lambda表达式
    Function<Integer, Employee> function = id -> new Employee(id);
    Employee employee = function.apply(12);
    System.out.println(employee);

    // 构造器引用
    Function<Integer, Employee> function1 = Employee::new;
    Employee employee1 = function1.apply(50);
    System.out.println(employee1);
}

// BiFunction中的 R apply(T t, R r)
public void test3() {
    BiFunction<Integer, String, Employee> biFunction = Employee::new;
    Employee employee = biFunction.apply(20, "zhangsan");
    System.out.println(employee);
}

数组引用

// 数组引用
// Function中的R apply(T t)
public void test4() {
    // lambda表达式
    Function<Integer, String[]> function = length -> new String[length];
    String[] strings = function.apply(5);
    System.out.println(Arrays.toString(strings));

    // 数组引用
    Function<Integer, String[]> function1 = String[] ::new;
    String[] strings1 = function1.apply(6);
    System.out.println(Arrays.toString(strings1));
}
  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值