JAVA的函数式接口

目录

菜鸡小白为了巩固才写的。

一、函数式接口的简单介绍

        函数标识符: 函数式接口的抽象方法被称为“函数描述符”。这个描述符包含了方法的返回类型、方法名称以及参数类型的信息。编译器利用这些信息来判断一个 Lambda 表达式是否可以被用作该接口的实现。

二、函数式接口的样例

三、泛型函数式接口

        1、JDK自带泛型函数式接口:

                (1)Function:接收一个参数,返回一个结果。,>

                (2)Consumer:接收一个参数,没有返回值(通常用于执行某种操作)。

                (3)Supplier:不接受参数,返回一个结果。

                (4)Predicate:接收一个参数,返回一个布尔值(通常用于测试条件)。

                (5)BiFunction:接收两个参数,返回一个结果。,>

        2、自定义泛型函数式接口:


一、函数式接口的简单介绍

  1. 所谓“函数式接口”,就是“只定义有一个抽象方法的接口”(绝对绝对只有一个抽象方法),在Java 8之前,这种接口被称为“SAMSingle Abstract Method”接口。换而言是函数式接口就是只定义一个抽象方法的接口。这个抽象方法,它的名字不重要,它的输入参数和返回值类型才重要。
  2. 函数式接口只能有一个抽象方法,但并非只能有一个方法,默认,私有,静态都可以。同时静态方法还有这样的特性:只要实现了这个接口的所有类,都自动拥有这个静态方法。
  3. 能接收一个Lambda表达式的变量,必须是接口类型,并且这种接口,还必须是一种“函数式接口(functional interface”。
  4. Java 8中,使用“@FunctionalInterface”标识一个“函数式接口”。定义函数式接口时,
    @FunctionalInterface 注解不是必需的,但如果你加入了这个注解,而你定义的接口又不符合函数式接口的要求时,则Java 编译器会给出提示, 要你修正错误。所以,推荐加入这个注解。
  5. 简单的自定义的函数式接口的示例
    @FunctionalInterface
    public interface Runnable {
        public abstract void run();//函数标识符
    }
        函数标识符: 函数式接口的抽象方法被称为“函数描述符”。这个描述符包含了方法的返回类型、方法名称以及参数类型的信息。编译器利用这些信息来判断一个 Lambda 表达式是否可以被用作该接口的实现。

二、函数式接口的样例

        样例一:

public class Test1 {
    @FunctionalInterface
    interface Print{
        void print();
        static void printf(){
            System.out.println("Hello World");
        }
    }
    public static class P implements Print{
        public void print(){
            System.out.println("Print");
        }
        public void printf(){
            System.out.println("HW");
        }
    }
    public static void main(String[] args) {
        P p = new P();
        p.printf();
        p.print();
    }
}

这就是一个简单的函数式接口的样例。可见当函数式接口的静态函数与实现该接口的类的方法名冲突后,会重写冲突的方法。

        样例二:

@FunctionalInterface
public interface MyFunctionalInterface {
    //接口常量
    final int MAX_VALUE = 255;
    //唯一的抽象公有方法
    void func();
    //放置Object类的公有方法
    int hashCode();
    String toString();
    boolean equals(Object obj);

    private void instancePrivateMethod() {
        System.out.println("JDK9新增:接口中的私有实例方法");
    }

    default void defaultMethod() {
        System.out.println("JDK8新增:接口中的默认方法");
        instancePrivateMethod();  //调用接口中的私有实例方法
    }

    private static void staticPrivateMethod() {
        System.out.println("JDK9新增,接口中的私有静态方法");
    }

    static void staticMethod() {
        System.out.println("JDk8新增:接口中的静态方法");
        staticPrivateMethod();//调用接口中的私有静态方法
    }
}

//此类自动拥有接口所定义的默认方法和静态方法
class MyFunctionalClass implements MyFunctionalInterface {
    @Override
    public void func() {
        System.out.println("调用MyFunctionalClass.func()");
    }
}

class UseMyFunctionalInterface {
    public static void main(String[] args) {
        //调用接口的静态方法
        MyFunctionalInterface.staticMethod();
        //访问接口中的常量字段
        System.out.println(MyFunctionalInterface.MAX_VALUE);
        System.out.println("\n=========================\n");
        //实例化一个实现了接口的类
        MyFunctionalInterface obj = new MyFunctionalClass();
        //通过接口变量访问接口中的成员
        obj.func();
        obj.defaultMethod();
        System.out.println(obj.hashCode());
        System.out.println("\n=========================\n");
        //让接口变量接收一个Lambda表达式
        obj=()->System.out.println("将Lambda表达式赋值给接口变量");
        obj.func();
        obj.defaultMethod();
        System.out.println(obj.hashCode());
    }
}

输出结果:

JDk8新增:接口中的静态方法
JDK9新增,接口中的私有静态方法
255

=========================

调用MyFunctionalClass.func()
JDK8新增:接口中的默认方法
JDK9新增:接口中的私有实例方法
2003749087

=========================

将Lambda表达式赋值给接口变量
JDK8新增:接口中的默认方法
JDK9新增:接口中的私有实例方法
990368553

这就是一个函数式接口的综合体现。

三、泛型函数式接口

        JDK提供了很多内置的函数式接口可供使用,这些接口大多定义为泛型接口。

        1、JDK自带泛型函数式接口:

                (1)Function<T, R>:接收一个参数,返回一个结果。
import java.util.function.Function;

Function<Integer, String> intToString = Object::toString;
String result = intToString.apply(123); // 输出 "123"
                (2)Consumer<T>:接收一个参数,没有返回值(通常用于执行某种操作)。
import java.util.function.Consumer;

Consumer<String> print = System.out::println;
print.accept("Hello, World!"); // 输出 "Hello, World!"
                (3)Supplier<T>:不接受参数,返回一个结果。
import java.util.function.Supplier;

Supplier<String> getString = () -> "Hello, Supplier!";
String str = getString.get(); // 输出 "Hello, Supplier!"
                (4)Predicate<T>接收一个参数,返回一个布尔值(通常用于测试条件)。
import java.util.function.Predicate;

Predicate<String> isEmpty = String::isEmpty;
boolean result = isEmpty.test(""); // 输出 true
                (5)BiFunction<T, U, R>接收两个参数,返回一个结果。
import java.util.function.BiFunction;

BiFunction<Integer, Integer, Integer> add = (a, b) -> a + b;
Integer sum = add.apply(5, 10); // 输出 15

        2、自定义泛型函数式接口:

                当我们去了解了JDK提供的泛型函数式接口的源码,我们可以依葫芦画瓢,自定义

import java.util.function.Function;
@FunctionalInterface
interface TriFunction<T, U, V, R> {
    R apply(T t, U u, V v);
}
public class UseGenericFunctionInterface {
    public static void main(String[] args) {
        useJDKFunctionInterface();

        useMyGenericFunctionInterface();
    }

    private static void useMyGenericFunctionInterface() {
        TriFunction<Integer, Integer, Integer, Integer> add3Number =
                (x, y, z) -> x + y + z;
        //输出:6
        System.out.println(add3Number.apply(1,2,3));
    }

    private static void useJDKFunctionInterface() {
        //接收的Lambda表达式满足以下要求
        //(1)接收一个String类型的字符串参数
        //(2)返回一个Integer类型的结果
        Function<String, Integer> stringLength = str -> str.length();
        //通过apply()方法调用
        System.out.println(stringLength.apply("Hello")); // 5
    }
}

        以上代码中展示了自定义的简单的的泛型接口式函数以及对JDK提供的泛型接口式函数的简单调用。

### Java 函数式接口概述 函数式接口是指只包含一个抽象方法的接口。这类接口Java 8 引入的概念,旨在支持函数式编程风格,并允许通过 lambda 表达式来简化代码实现[^2]。 为了确保某个接口确实是函数式接口,在定义时可以使用 `@FunctionalInterface` 注解。此注解并非必需,但它能帮助开发者明确意图并让编译器验证接口是否满足单一抽象方法的要求[^3]。 ### 常见内置函数式接口及其用途 Java 提供了一些常用的预定义函数式接口: - **Consumer<T>**: 接受单个输入参数而不返回任何结果的操作。 - **Predicate<T>**: 接受单个输入参数并返回布尔值的结果判断逻辑。 - **Function<T, R>**: 接收 T 类型的对象作为输入,并转换成另一种类型 R 的对象输出。 - **Supplier<T>**: 不接受参数而提供某种类型的对象实例的方法。 这些接口通常应用于集合框架的数据流处理中,比如利用 Stream API 进行排序、过滤、映射等操作[^4]。 ### 自定义函数式接口示例 除了上述标准库提供的接口外,还可以创建自定义的函数式接口以适应特定需求。下面是一个简单的例子展示如何声明和使用这样的接口: ```java // 定义一个名为 Greeting 的函数式接口 @FunctionalInterface interface Greeting { void sayHello(String name); } public class Main { public static void main(String[] args) { // 使用 Lambda 表达式实现该接口 Greeting greet = (name) -> System.out.println("Hello " + name); // 调用接口中的唯一方法 greet.sayHello("World"); } } ``` 这段代码展示了如何定义一个带有单一抽象方法的接口以及怎样借助 lambda 表达式快速构建其实现方式。 ### 数据处理应用案例 当涉及到复杂的数据集变换任务时,函数式接口配合 Streams 可极大提高开发效率。例如,假设有一组整数列表需要筛选偶数值后再平方每项,则可按如下方式编写简洁高效的解决方案: ```java import java.util.Arrays; import java.util.List; import java.util.stream.Collectors; List<Integer> numbers = Arrays.asList(1, 2, 3, 4, 5, 6); List<Integer> squaredEvens = numbers.stream() .filter(n -> n % 2 == 0) // Predicate<T> .map(n -> n * n) // Function<T,R> .collect(Collectors.toList()); System.out.println(squaredEvens); // 输出 [4, 16, 36] ``` 这里运用了多个不同的函数式接口来完成一系列连续性的数据加工步骤。
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值