Functional Interface

Functional Interface是什么?

功能接口是java 8中的新增功能,它们只允许一个抽象方法。这些接口也称为单抽象方法接口(SAM接口)。这些也可以使用Lambda表达式,方法引用和构造函数引用来表示。Java 8也引入了一个注释,即@FunctionalInterface,当你注释的接口违反了Functional Interface的契约时,它可以用于编译器级错误。

Tips:如果你想强制当前接口只保留一个抽象方法,就可以使用@FunctionalInterface,它可以帮我们通过编译错误提示用户必须不能声明超过一个抽象方法

构建我们第一个默认接口:

@FunctionalInterface
public interface MyFuntinoalInterface<T> { public void eat();
/**
* 超过一个抽象方法会编译报错,可以把下面注释去掉查看效果
*/
//public void play();
}

尝试将上例的注释去掉,可以发现,超过两个抽象方法会直接报编译错误

@FunctionalInterface
public interface MyFuntinoalInterface<T> { public void eat();
/**
* 超过一个抽象方法会编译报错,可以把下面注释去掉查看效果
*/
public void play();
}

报如下编译异常:

功能接口的使用原则

  • 在任何功能接口中只允许一种抽象方法。功能界面中不允许使用第二种抽象方法。如果我们删除@FunctionInterface注释,那么我们可以添加另一个抽象方法,但它会使接口成为非功能性接口。
  • 即使省略@FunctionalInterface注释,功能接口也是有效的。它仅用于通知编译器在接口内强制执行单个抽象方法。
  • 从概念上讲,功能界面只有一种抽象方法。由于默认方法具有实现,因此它们不是抽象的。由于默认方法不是抽象的,因此您可以根据需要随意添加默认方法到功能接口。

你可以添加多个默认方法到功能接口中,但是它不会计入抽象方法的数量:

@FunctionalInterface
public interface MyFuntinoalInterface<T> { public void eat(); default void run(){
System.out.println("跑步");
} default void swim(){
System.out.println("游泳");
}
}
  • 功能接口里可以有多个覆盖java.lang.Objectd的抽象方法,它不会计入接口的抽象方法数量。
@FunctionalInterface
public interface MyFuntinoalInterface<T> { public void eat(); /**
* 重写Object方法不会算入抽象方法统计
* @return
*/
@Override
public String toString();
}

JDK 中的功能接口

JDK1.8开始支持功能接口,以下可以举几个例子,功能接口主要是配合lambda表达式使用,具体介绍会在后续的lambda表达式章节也会提到

Comparator

@FunctionalInterface
public interface Comparator<T>

在JDK1.8中,主要对Comparator接口添加了默认方法,对Comparator实现类添加了很多新特性方法

Consumer

@FunctionalInterface
public interface Consumer<T>

相信大家查看JDK1.8源码会发现,很多类都有Consumer这个接口存在,在JDK1.8中更多是提供各个接口支持lambda表达式使用

Iterable

public interface Iterable<T> {
/**
* Returns an iterator over elements of type {@code T}.
*
* @return an Iterator.
*/
Iterator<T> iterator(); /**
* Performs the given action for each element of the {@code Iterable}
* until all elements have been processed or the action throws an
* exception. Unless otherwise specified by the implementing class,
* actions are performed in the order of iteration (if an iteration order
* is specified). Exceptions thrown by the action are relayed to the
* caller.
*
* @implSpec
* <p>The default implementation behaves as if:
* <pre>{@code
* for (T t : this)
* action.accept(t);
* }</pre>
*
* @param action The action to be performed for each element
* @throws NullPointerException if the specified action is null
* @since 1.8
*/
default void forEach(Consumer<? super T> action) {
Objects.requireNonNull(action);
for (T t : this) {
action.accept(t);
}
} /**
* Creates a {@link Spliterator} over the elements described by this
* {@code Iterable}.
*
* @implSpec
* The default implementation creates an
* <em><a href="Spliterator.html#binding">early-binding</a></em>
* spliterator from the iterable's {@code Iterator}. The spliterator
* inherits the <em>fail-fast</em> properties of the iterable's iterator.
*
* @implNote
* The default implementation should usually be overridden. The
* spliterator returned by the default implementation has poor splitting
* capabilities, is unsized, and does not report any spliterator
* characteristics. Implementing classes can nearly always provide a
* better implementation.
*
* @return a {@code Spliterator} over the elements described by this
* {@code Iterable}.
* @since 1.8
*/
default Spliterator<T> spliterator() {
return Spliterators.spliteratorUnknownSize(iterator(), 0);
}
}

Iterable虽然接口头上没有@FunctionalInterface注解标注,它这里只有一个抽象方法,默认也是一个功能接口,在JDK1.8中新添加了支撑lambda表达式的默认方法

Java8新特性一点通 | 回顾功能接口Functional Interface的更多相关文章

  1. Java8新特性一点通 | 回顾字符转日期&JoinArray使用

    StringToDate日期转换 Join Array使用 StringToDate日期转换 Convert string to date in ISO8601 format 利用LocalDate. ...

  2. Java8新特性一点通 | 回顾文件操作和watchService文件变更监视操作

    文件操作 WatchService 文件操作 今天重温了一些文件操作: - Files.list() 遍历文件和目录 //List all files and sub-directories usin ...

  3. Java8新特性—四大内置函数式接口

    Java8新特性--四大内置函数式接口 预备知识 背景 Lambda 的设计者们为了让现有的功能与 Lambda 表达式良好兼容,考虑了很多方法,于是产生了函数接口这个概念. 什么是函数式接口? 函数 ...

  4. java8新特性—四大内置核心接口

    java8新特性-四大内置核心接口 四大内置核心接口 //消费型接口 Consumer<T>:: vode accept(T t); //供给型接口 Supplier<T>:: ...

  5. Java8新特性_lambda表达式和函数式接口最详细的介绍

    Lambda表达式 在说Lambda表达式之前我们了解一下函数式编程思想,在数学中,函数就是有输入量.输出量的一套计算方案,也就是“拿什么东西做什么事情”. 相对而言,面向对象过分强调“必须通过对象的 ...

  6. Java8新特性时间日期库DateTime API及示例

    Java8新特性的功能已经更新了不少篇幅了,今天重点讲解时间日期库中DateTime相关处理.同样的,如果你现在依旧在项目中使用传统Date.Calendar和SimpleDateFormat等API ...

  7. Java8新特性(一)——Lambda表达式与函数式接口

    一.Java8新特性概述 1.Lambda 表达式 2. 函数式接口 3. 方法引用与构造器引用 4. Stream API 5. 接口中的默认方法与静态方法 6. 新时间日期 API 7. 其他新特 ...

  8. JAVA8新特性——接口定义增强

    JAVA9都要出来了,JAVA8新特性都没搞清楚,是不是有点掉队哦~ 接口定义增强 在JDK1.8以前,接口是定义的: 接口(英文:Interface),在JAVA编程语言中是一个抽象类型,是抽象方法 ...

  9. java8新特性学习:函数式接口

    本文概要 什么是函数式接口? 如何定义函数式接口? 常用的函数式接口 函数式接口语法注意事项 总结 1. 什么是函数式接口? 函数式接口其实本质上还是一个接口,但是它是一种特殊的接口:SAM类型的接口 ...

随机推荐

  1. 算法复杂度之 空间复杂度(Java)

    0.说明 根据算法书上的定义,一个算法的空间复杂度包括算法程序所占用的空间,输入初始数据所占用的空间以及算法执行过程中所需要的额外空间.本文各种结论全部参考过标准文献,本人也进行过验证.验证过程本文不 ...

  2. dockerfile部署tomcat+jdk

    FROM centos: MAINTAINER www.ctnrs.com ENV VERSION= RUN yum install wget curl unzip iproute net-tools ...

  3. Python中三大框架各自的应用场景(DJango,flask,Tornado)

    django:主要是用来搞快速开发的,他的亮点就是快速开发,节约成本,正常的并发量不过10000,如果要实现高并发的话,就要对django进行二次开发,比如把整个笨重的框架给拆掉,自己写socket实 ...

  4. 斜率优化入门题题单$QwQ$

    其实就是这一篇的那个例题帕的大部分题目的题解就写这儿辣,,, 因为都是些基础题不想专门给写题解,,,但是又掌握得差不得不写,,, 麻油办法就写一块儿好辣$QwQ$ 当然辣比较难的我就没放进来辣$QwQ ...

  5. <算法><go实现>左括号补全-双栈法

    输入:1+2)*33-44)*555-666))) 输出:((1+2)*((33-44)*(555-666))) 代码实现及注释: package main import "fmt" ...

  6. 【一起学源码-微服务】Feign 源码二:Feign动态代理构造过程

    前言 前情回顾 上一讲主要看了@EnableFeignClients中的registerBeanDefinitions()方法,这里面主要是 将EnableFeignClients注解对应的配置属性注 ...

  7. 为QLabel增加Clicked信号

    QT为QLabel添加Click事件(如果我们使用组件,我们关心的是信号槽:如果我们自定义组件,我们关心的是事件) 其实就是改写了一个函数:mouseReleaseEvent,当在QLabel放开鼠标 ...

  8. 一个C#开发者重温Java的心路历程

    前言 我们都知道软件开发是工科,不是理科:本质上和电工.钳工是一样的. 也就是说,软件技术成长也与电工.钳工的技术成长是一样的,靠的是练,而不是学. 所以,很多时候,我们称应届大学生是一张白纸,啥也不 ...

  9. Spring Boot从零入门2_核心模块详述和开发环境搭建

    目录 1 前言 2 名词术语 3 Spring Boot核心模块 3.1 spring-boot(主模块) 3.2 spring-boot-starters(起步依赖) 3.3 spring-boot ...

  10. mysql 多主一从

    一.主服务器准备 1.1.环境准备 两台主机器ip分别为 100.100.100.105 (主1) 100.100.100.106(主2) 安装 mysql [root@centos ~]# yum ...