匿名内部类和Lambda

目录

1、在抽象类上使用匿名内部类

2、在接口上使用匿名内部类

3、总结

二、Lambda

1、函数式接口

2、FunctionalInterface

三、Lambda和匿名内部类在使用上的区别

四、常用接口

1、Supplier——无参有返回值

2、Comsumer——有参无返回值

3、Function——一个参数,一个返回值

4、Predicate——一个参数,返回boolean

五、方法引用的格式

1、应用场景:

2、方法引用有以下几种格式


一、匿名内部类

匿名内部类也就是没有名字的内部类

正因为没有名字,所以匿名内部类只能使用一次,它通常用来简化代码编写

但使用匿名内部类还有个前提条件:必须继承一个父类或实现一个接口

1、在抽象类上使用匿名内部类

public class Test {
    public static void main(String[] args) {
        Animal animal = new Animal() {
            @Override
            void eat() {
                System.out.println("eat");
            }

            @Override
            void cry() {
                System.out.println("cry");
            }
        };
        animal.eat();
        animal.cry();
        animal.show();
    }
}

abstract class Animal {
    abstract void eat();
    abstract void cry();
    void show() {
        System.out.println("show");
    }
}

运行结果:

eat
cry
show

2、在接口上使用匿名内部类

public class Test {
    public static void main(String[] args) {
        Animal animal = new Animal() {
            @Override
            public void eat() {
                System.out.println("abstract===eat");
            }

            @Override
            public void cry() {
                System.out.println("abstract===cry");
            }
        };
        animal.eat();
        animal.cry();
        Animal.show();
        Animal.show1();
        animal.show2();
    }
}

interface Animal {
    void eat();

    void cry();

    static void show() {
        System.out.println("static===show===接口的static方法只能使用接口名.方法名来调用,且可以有多个static方法");
    }

    static void show1() {
        System.out.println("static===show1");
    }

    default void show2() {
        System.out.println("default===show2===接口有且只能有一个default方法");
    }
}

运行结果:

abstract===eat
abstract===cry
default===show2
接口的static方法只能使用接口名.方法名来调用,且可以有多个static方法
static===show1

3、总结

只要一个类是抽象的或是一个接口,那么其子类中的方法都可以使用匿名内部类来实现

二、Lambda

1、函数式接口

有且仅有一个抽象方法,但是可以有多个非抽象方法的接口。函数式接口可以被隐式转换为lambda表达式。

public class Test {
    public static void main(String[] args) {
        Animal animal = () -> System.out.println("eat");
        animal.eat();
        Animal.show();
        Animal.show1();
        animal.show2();
    }
}

@FunctionalInterface
interface Animal {
    void eat();

    static void show() {
        System.out.println("static===show===接口的static方法只能使用接口名.方法名来调用,且可以有多个static方法");
    }

    static void show1() {
        System.out.println("static===show1");
    }

    default void show2() {
        System.out.println("default===show2===接口有且只能有一个default方法");
    }
}

2、FunctionalInterface

@FunctionalInterface检测接口是否属于函数式接口

三、Lambda和匿名内部类在使用上的区别

1、所需的类型不一样
匿名内部类,需要的类型可以是抽象类、接口
Lambda表达式需要的类型必须是接口
2、抽象方法的数量不一样
匿名内部类所需的接口中抽象方法的数量随意
Lambda表达式所需的接口只能有一个抽象方法
3、实现原理不同
匿名内部类在编译后会形成class
Lambda表达式时在程序运行的时候生成class

四、常用接口

1、Supplier——无参有返回值

.get

2、Comsumer——有参无返回值

.accept
.andThen

3、Function——一个参数,一个返回值

.apply
.andThen

4、Predicate——一个参数,返回boolean

.test
.and
.or

import cn.hutool.core.date.DateUtil;

import java.util.function.Consumer;
import java.util.function.Function;
import java.util.function.Predicate;
import java.util.function.Supplier;

public class Test {
    public static void main(String[] args) {
        testOfSupplier(() -> DateUtil.now());

        testOfConsumer(str -> System.out.println(Integer.parseInt(str)), "1024");

        testOfConsumer(str -> System.out.print("consumer-" + str), str -> System.out.println("===consumer2-" + str), "hello");

        testOfFunction(num -> "===入参:" + num + "===运算后的返回值:" + num * 5, 12);

        testOfFunction(num -> "Hello" + num, str -> str.length(), 12);

        testOfPredicate(num -> num > 12, 11);

        testOfPredicate2(num -> num > 12, 11);

        testOfPredicate(num -> num > 10, num -> num < 20, 12);
        testOfPredicate(num -> num > 10, num -> num > 20, 12);

    }

    public static void testOfSupplier(Supplier<String> supplier) {
        System.out.println("===Supplier.get===:" + supplier.get());
    }

    public static void testOfConsumer(Consumer<String> consumer, String str) {
        System.out.print("===Consumer.accept===:");
        consumer.accept(str);
    }

    public static void testOfConsumer(Consumer<String> consumer, Consumer<String> consumer2, String str) {
        System.out.print("===Consumer.andThen===:");
        consumer.andThen(consumer2).accept(str);
    }


    public static void testOfFunction(Function<Integer, String> function, Integer num) {
        System.out.println("===Function.apply===:" + function.apply(num));
    }

    public static void testOfFunction(Function<Integer, String> function, Function<String, Integer> function2, Integer num) {
        System.out.println("===Function.andThen===:" + function.andThen(function2).apply(num));
    }

    public static void testOfPredicate(Predicate<Integer> predicate, Integer num) {
        System.out.println("===Predicate.test===:" + predicate.test(num));
    }

    public static void testOfPredicate2(Predicate<Integer> predicate, Integer num) {
        System.out.println("===Predicate.negate===:" + predicate.negate().test(num));
    }

    public static void testOfPredicate(Predicate<Integer> predicate, Predicate<Integer> predicate2, Integer num) {
        System.out.println("===Predicate.and===num:" + num + "==是否大于10小于20:" + predicate.and(predicate2).test(num));
    }

    public static void testOfPredicate2(Predicate<Integer> predicate, Predicate<Integer> predicate2, Integer num) {
        System.out.println("===Predicate.or===num:" + num + "==是否小于10或大于20:" + predicate.or(predicate2).test(num));
    }


}

五、方法引用的格式

1、应用场景:

如果Lambda所要实现的方案,已经有其他方法存在的方案,那么那么可以使用方法引用。

2、方法引用有以下几种格式

1、instaceName::methoidName      实例::方法名 
2、ClassName::staticMethodName   类名::静态方法
3、ClassName::methoidName         类名::普通方法  例如String
4、Class::new                    类名::new 调用的构造器
5、TypeName[]::new 

import lombok.AllArgsConstructor;
import lombok.Data;
import lombok.NoArgsConstructor;

import java.util.Arrays;
import java.util.function.Consumer;
import java.util.function.Function;
import java.util.function.Supplier;

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

        Test2 test2 = new Test2();
        int[] arr = {1, 2, 3, 4};
        test2.show(arr);

        Consumer<int[]> consumer = new Consumer<int[]>() {
            @Override
            public void accept(int[] ints) {
                int sum = 0;
                for (int i = 0; i < arr.length; i++) {
                    sum += arr[i];
                }
                System.out.println("arr:" + Arrays.toString(arr) + "===sum:" + sum);
            }
        };
        consumer.accept(arr);

        Consumer<int[]> consumer2 = test2::show;
        consumer2.accept(arr);

        System.out.println(Test2.staticMethod("10"));

        Function<String, Integer> function = str -> {
            int i = Integer.parseInt(str);
            System.out.print("入参num:" + str + "转换后结果为===");
            return i * 20;
        };
        System.out.println(function.apply("20"));

        Function<String, Integer> function2 = Test2::staticMethod;
        System.out.println(function2.apply("20"));

        Supplier<Cat> supplier = () -> new Cat("小花", 12);
        System.out.println(supplier.get());

        Supplier<Cat> supplier2 = Cat::new;
        System.out.println(supplier2.get());


        Function<Integer, int[]> function1 = int[]::new;
        System.out.println(Arrays.toString(function1.apply(10)));

    }

    public void show(int[] arr) {
        int sum = 0;
        for (int i = 0; i < arr.length; i++) {
            sum += arr[i];
        }
        System.out.println("arr:" + Arrays.toString(arr) + "===sum:" + sum);

        Function<String, Integer> function = String::length;
    }


    public void showCatName(Cat cat) {

        System.out.println("===" + cat.getName());
    }

    public static Integer staticMethod(String num) {
        int i = Integer.parseInt(num);
        System.out.print("入参num:" + num + "转换后结果为===");
        return i * 20;
    }

}

@Data
@NoArgsConstructor
@AllArgsConstructor
class Cat {
    private String name;
    private Integer age;
}

 

 

 

 

  • 0
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值