热门标签 | HotTags
当前位置:  开发笔记 > 编程语言 > 正文

Java8Lambda基础之函数接口

什么是函数接口?函数接口英文全称是FunctionalInterface,是一种可用于Lambda表达式的接口,该概念在JDK8首次被提出,关于FunctionalInterfac

什么是函数接口?

函数接口英文全称是FunctionalInterface,是一种可用于Lambda表达式的接口,该概念在JDK 8首次被提出,关于FunctionalInterface JDK官方文档的解释是

* Conceptually, a functional interface has exactly one abstract

* method. Since {@linkplain java.lang.reflect.Method#isDefault()

* default methods} have an implementation, they are not abstract. If

* an interface declares an abstract method overriding one of the

* public methods of {@code java.lang.Object}, that also does

* not count toward the interface’s abstract method count

* since any implementation of the interface will have an

* implementation from {@code java.lang.Object} or elsewhere.

从中我们得知一个functional interface 有且只有一个抽像方法。比如我们常见的Runnable接口

@FunctionalInterface
public interface Runnable {
/** * When an object implementing interface Runnable is used * to create a thread, starting the thread causes the object's * run method to be called in that separately executing * thread. *

* The general contract of the method run is that it may * take any action whatsoever. * * @see java.lang.Thread#run() */
public abstract void run();
}

但functional interface中并不限制有非抽像方法存在比如Java8 后引进的default方法。以Stream.forEach中常用的Consumer接口为例,里面就带了一个andThen的非抽像方法。

@FunctionalInterface
public interface Consumer<T> {
/** * Performs this operation on the given argument. * * @param t the input argument */
void accept(T t);
default Consumer<T> andThen(Consumer super T> after) {
Objects.requireNonNull(after);
return (T t) -> { accept(t); after.accept(t); };
}
}

除此之外functional interface还不限制存在Object类中定义的公有接口的方法,因为这本来就是Interface中隐式声明的。即使显示声明也不会计算进抽像方法中。比如JDK自带的Comparator里面就定义了两个抽像方法,但因为equals是Object类公有的方法。所以equals方法不会被计算进抽像方法个数。Comparator依然是个function interface。

@FunctionalInterface
public interface Comparator<T> {
int compare(T o1, T o2); boolean equals(Object obj);
}

所以总的来说,函数接口是只有一个抽像方法,但可以抽像定义Object类公有方法和存在default方法的一类接口。

创建实例

一般接口实例的创建是implement该接口的对象,函数接口也不例外。但函数接口的特别之外在于Lambda表达式方面的应用,它可以被lambda expression、method references、 constructor references创建。可以说lambda表礞式创建的所有对象都是函数接口实例。

下面是三种创建的例子

Runnable runnable = () -> System.out.println("lambda expression"); //lambda expression Comparator<String> comparing = Comparator.comparing(String::length); //method references BiConsumer<File, String> fileStringBiConsumer = File::new; //constructor references

另外函数接口之所以限制只有一个抽像方法的原因,是因为这个抽像方法代表了lambda expression要实现的函数类型。如果有多个抽像方法lambda expression根本不知道实现的是哪个方法。另外抽像方法的参数个类、参数类型以及返回值、异常定义是编译器进行类型推断的依据。

泛型问题

比如有以下三个接口:

@FunctionalInterface
public interface Foo extends Foo1, Foo2 {
void bar(List args);}
interface Foo1 {
void bar(List<String> args);
}
interface Foo2 {
void bar(List<Integer> args);
}

看上去Foo 继承了Foo1, Foo2两个接口。这两个接口又各自了一个抽像方法,Foo又定义了一个抽像方法。这样Foo就有三个抽像方法了,不可能是一个funtion interface。但实际上因为Java泛型会有一个类型擦除动作。所以这三个接口的方法实际都是:

void bar(List args);

这样Foo的抽像方法相当于覆盖了Foo1,Foo2的接口中的抽像方法,就是只有一个。所以Foo可以看作是function inferface。


推荐阅读
  • 前景:当UI一个查询条件为多项选择,或录入多个条件的时候,比如查询所有名称里面包含以下动态条件,需要模糊查询里面每一项时比如是这样一个数组条件:newstring[]{兴业银行, ... [详细]
  • 本文主要解析了Open judge C16H问题中涉及到的Magical Balls的快速幂和逆元算法,并给出了问题的解析和解决方法。详细介绍了问题的背景和规则,并给出了相应的算法解析和实现步骤。通过本文的解析,读者可以更好地理解和解决Open judge C16H问题中的Magical Balls部分。 ... [详细]
  • Python正则表达式学习记录及常用方法
    本文记录了学习Python正则表达式的过程,介绍了re模块的常用方法re.search,并解释了rawstring的作用。正则表达式是一种方便检查字符串匹配模式的工具,通过本文的学习可以掌握Python中使用正则表达式的基本方法。 ... [详细]
  • 个人学习使用:谨慎参考1Client类importcom.thoughtworks.gauge.Step;importcom.thoughtworks.gauge.T ... [详细]
  • 本文介绍了UVALive6575题目Odd and Even Zeroes的解法,使用了数位dp和找规律的方法。阶乘的定义和性质被介绍,并给出了一些例子。其中,部分阶乘的尾零个数为奇数,部分为偶数。 ... [详细]
  • 怎么在PHP项目中实现一个HTTP断点续传功能发布时间:2021-01-1916:26:06来源:亿速云阅读:96作者:Le ... [详细]
  • 本文讨论了在手机移动端如何使用HTML5和JavaScript实现视频上传并压缩视频质量,或者降低手机摄像头拍摄质量的问题。作者指出HTML5和JavaScript无法直接压缩视频,只能通过将视频传送到服务器端由后端进行压缩。对于控制相机拍摄质量,只有使用JAVA编写Android客户端才能实现压缩。此外,作者还解释了在交作业时使用zip格式压缩包导致CSS文件和图片音乐丢失的原因,并提供了解决方法。最后,作者还介绍了一个用于处理图片的类,可以实现图片剪裁处理和生成缩略图的功能。 ... [详细]
  • 本文讨论了一个数列求和问题,该数列按照一定规律生成。通过观察数列的规律,我们可以得出求解该问题的算法。具体算法为计算前n项i*f[i]的和,其中f[i]表示数列中有i个数字。根据参考的思路,我们可以将算法的时间复杂度控制在O(n),即计算到5e5即可满足1e9的要求。 ... [详细]
  • 纠正网上的错误:自定义一个类叫java.lang.System/String的方法
    本文纠正了网上关于自定义一个类叫java.lang.System/String的错误答案,并详细解释了为什么这种方法是错误的。作者指出,虽然双亲委托机制确实可以阻止自定义的System类被加载,但通过自定义一个特殊的类加载器,可以绕过双亲委托机制,达到自定义System类的目的。作者呼吁读者对网上的内容持怀疑态度,并带着问题来阅读文章。 ... [详细]
  • 基于Socket的多个客户端之间的聊天功能实现方法
    本文介绍了基于Socket的多个客户端之间实现聊天功能的方法,包括服务器端的实现和客户端的实现。服务器端通过每个用户的输出流向特定用户发送消息,而客户端通过输入流接收消息。同时,还介绍了相关的实体类和Socket的基本概念。 ... [详细]
  • 本文介绍了Android中的assets目录和raw目录的共同点和区别,包括获取资源的方法、目录结构的限制以及列出资源的能力。同时,还解释了raw目录中资源文件生成的ID,并说明了这些目录的使用方法。 ... [详细]
  • ***byte(字节)根据长度转成kb(千字节)和mb(兆字节)**parambytes*return*publicstaticStringbytes2kb(longbytes){ ... [详细]
  • 本文介绍了一种在PHP中对二维数组根据某个字段进行排序的方法,以年龄字段为例,按照倒序的方式进行排序,并给出了具体的代码实现。 ... [详细]
  • 本文整理了Java中java.lang.NoSuchMethodError.getMessage()方法的一些代码示例,展示了NoSuchMethodErr ... [详细]
  • 本文介绍了关于Java异常的八大常见问题,包括异常管理的最佳做法、在try块中定义的变量不能用于catch或finally的原因以及为什么Double.parseDouble(null)和Integer.parseInt(null)会抛出不同的异常。同时指出这些问题是由于不同的开发人员开发所导致的,不值得过多思考。 ... [详细]
author-avatar
lily0407520
这个家伙很懒,什么也没留下!
PHP1.CN | 中国最专业的PHP中文社区 | DevBox开发工具箱 | json解析格式化 |PHP资讯 | PHP教程 | 数据库技术 | 服务器技术 | 前端开发技术 | PHP框架 | 开发工具 | 在线工具
Copyright © 1998 - 2020 PHP1.CN. All Rights Reserved | 京公网安备 11010802041100号 | 京ICP备19059560号-4 | PHP1.CN 第一PHP社区 版权所有