本文博主纯手敲,转载请注明出处。

由于最近项目中都是基于JDK8或JDK9,因此熟悉新版本中的特性尤其重要,这里主要讲解Java8中java.util.function下的的函数式接口声明。

谈到函数式接口,那不得不提的必然是@FunctionalInterface注解啦,望文知义,这个注解就是用在接口上的,被称为“功能接口”,那么什么是所谓的“功能接口”呢?又有哪些特性呢?下面一一道来。

功能函数就是有@FunctionInterface注解的接口,特性包括:

1、 接口中只能有一个抽象方法,但是可以有默认方法(被default修饰的方法),默认方法不是抽象方法,包含具体的方法体。这种设计主要是因为,对于功能接口来讲,一个接口只会提供一个逻辑上的方法,通过这个逻辑上的方法表达一个单一函数,单是指多个方法的其他方法需要是继承自Object的public方法,或者你要想绕过,就自己实现default。函数式接口自己本身一定是只有一个抽象方法。同时,如果是Object类的public方法,也是不允许的。官方的说明翻译如下: 如果一个接口I,I有一组抽象方法集合M,且这些方法都不是Object类的public签名方法,那么如果存在一个M中的方法m,满足:

m的签名是所有M中方法签名的子签名。

m对于M中的每个方法都是返回类型可替换的。 我的理解是说一个功能函数只能有一个实际方法的“映射”,下面举个例子说明:

首先,在一个功能接口中有且仅有一个非Object中的抽象方法

/*** 有且仅有一个,而且是非Object里的方法*/
@FunctionalInterface
public interface InterfaceTest {boolean equals(Object obj);//会报错,因为equals是Object的方法
}//下面这个就没问题了,因为有一个抽象方法,另外一个是Object的,可以共存
@FunctionalInterface
public interface InterfaceTest {boolean equals(Object obj);void foo();
}//下面这个就又不行了,因为必须是Object的public方法才可以,clone是protected的
@FunctionInterface
public interface InterfaceTest(){Object clone();void foo();
}
复制代码

以上总结为一句话就是:函数式接口,有且仅有一个抽象方法,Object的public方法除外。

下面来看一下Function接口中的方法: Function接口只是提供了一个apply方法,传入E返回R,源码如下:

@FunctionalInterface
public interface Function<T, R> {/*** Applies this function to the given argument.** @param t the function argument* @return the function result*/R apply(T t);
}
复制代码

那么提供一个这种抽象方法有什么意义呢?我的理解是可以把它看做我们实际方法的一种“映射”,这又是什么意思呢?看例子:

public class UserDao(){public User getUser(Integer userId){User user = getUSer(userId);//getUser的方法实现不用考虑,这里只是为了说明问题return user;}
}
复制代码

我们看看这个例子中的getUser方法是不是可以看做是Function中的applay方法的一个实现?传入的一种类型的参数,返回不同类型的结果。其实参数的类型和返回值类型也可以是相同的,即T可以与R相同。这里不说它是实现,我更喜欢称作它为“映射”。

那么有了这种映射,我们在调用这个getUser方法的时候就很方便了,可以使用lambda表达式,也可以使用方法引用了,因为lambda表达式和方法引用使用的前提就是必须有该方法对应的功能函数方法映射,哈哈,还是觉得映射比较合适。看下面例子:

import java.util.function.Function;public class UserService {public static void main(String[] args) {UserService service = new UserService();//lambda表达式写法User lamUser = service.getUser(id->new User(id,"name"+id,"123"),1);System.out.println(lamUser);//函数引用写法User user = service.getUser(UserDao::getUser, 1);System.out.println(user);}public User getUser(Function<Integer, ? extends User> func,Integer id){User user = func.apply(id);return user;}
}
复制代码

怎么样?到了这里是不是有点感觉了?嘿嘿,接着向下看,这才刚入门。。。

下面我们将看看Java8里java.util.function包下的函数式接口。其中包括FunctionPredicateSupplierConsumerOperator(没有Operator接口,只有类似BinaryOperator这样的接口)。

Function

Function的apply方法前边我们已经看到过了,这里再贴一遍:

@FunctionalInterface
public interface Function<T, R> {/*** Applies this function to the given argument.** @param t the function argument* @return the function result*/R apply(T t);
}
复制代码

函数意为将参数T传递给一个函数,返回R。即

其默认实现了3个default方法,分别是composeandThenidentity,对应的函数表达为:compose对应,体现嵌套关系;andThen对应,转换了嵌套的顺序;还有identity对应了一个传递自身的函数调用对应。从这里看出来,composeandThen对于两个函数f和g来说,f.compose(g)等价于g.andThen(f)。如果这里的关系式看的有点晕,那就解释一下:

Compose

 default <V> Function<V, R> compose(Function<? super V, ? extends T> before) {Objects.requireNonNull(before);return (V v) -> apply(before.apply(v));
}
复制代码

就是该方法中需要传入一个Function作为参数,在调用compose方法时,先调用一下传入的Function的apply方法,然后再调用本函数内的apply方法。

andThen

default <V> Function<T, V> andThen(Function<? super R, ? extends V> after) {Objects.requireNonNull(after);return (T t) -> after.apply(apply(t));
}
复制代码

相信这个不用说也明白了,就是先调用传入的Function的apply,再调用本接口中的applay方法。

identity

static <T> Function<T, T> identity() {return t -> t;
}
复制代码

这个方法就是一个静态方法,返回一个执行了apply()方法之后只会返回输入参数的函数对象。

看个例子吧:

public static void main(String[] args) {Function<Integer, Integer> name = e -> e * 2;Function<Integer, Integer> square = e -> e * e;int value = name.andThen(square).apply(3);System.out.println("andThen value=" + value);int value2 = name.compose(square).apply(3);System.out.println("compose value2=" + value2);Object identity = Function.identity().apply("huohuo");System.out.println(identity);
}
复制代码

限于篇幅,本文先讲到这里,下一篇我们一起来看看高阶函数。

转载于:https://juejin.im/post/5b72daaaf265da27e100e086

Java8 函数式编程之函数接口(上)相关推荐

  1. [一] java8 函数式编程入门 什么是函数式编程 函数接口概念 流和收集器基本概念...

    本文是针对于java8引入函数式编程概念以及stream流相关的一些简单介绍 什么是函数式编程?   java程序员第一反应可能会理解成类的成员方法一类的东西 此处并不是这个含义,更接近是数学上的函数 ...

  2. java中函数是什么_[一] java8 函数式编程入门 什么是函数式编程 函数接口概念 流和收集器基本概念...

    本文是针对于java8引入函数式编程概念以及stream流相关的一些简单介绍 什么是函数式编程? java程序员第一反应可能会理解成类的成员方法一类的东西 此处并不是这个含义,更接近是数学上的函数 看 ...

  3. java8函数式编程 视频_快速掌握Java8 Stream函数式编程技巧

    函数式编程优势"函数第一位",即函数可以出现在任何地方. 可以把函数作为参数传递给另一个函数,还可以将函数作为返回值. 让代码的逻辑更清晰更优雅. 减少了可变量(Immutable ...

  4. Java8函数式编程详解

    Java8 函数式编程详解 Author:Dorae Date:2017年11月1日23:03:26 转载请注明出处 说起Java8,可能很多人都已经知道其最大的改进,就是引入了Lambda表达式与S ...

  5. Java8函数式编程_8--设计和架构的原则

    1,免责声明,本文大部分内容摘自<Java8函数式编程>.在这本书的基础上,根据自己的理解和网上一些博文,精简或者修改.本次分享的内容,只用于技术分享,不作为任何商业用途.当然这本书是非常 ...

  6. Java8函数式编程语法入门

    Java8函数式编程语法入门 Java8中函数式编程语法能够精简代码. 使用Consumer作为示例,它是一个函数式接口,包含一个抽象方法accept,这个方法只有输入而无输出. 现在我们要定义一个C ...

  7. java8函数式编程实例

    什么是函数式编程 函数式编程是java8的一大特色,也就是将函数作为一个参数传递给指定方法.别人传的要么是基本数据类型,要么就是地址引用 ,我们要穿一个"动作". Stream 说 ...

  8. Java8函数式编程_9--使用Lambda表达式编写并发程序

    1,免责声明,本文大部分内容摘自<Java8函数式编程>.在这本书的基础上,根据自己的理解和网上一些博文,精简或者修改.本次分享的内容,只用于技术分享,不作为任何商业用途.当然这本书是非常 ...

  9. [2017.02.23] Java8 函数式编程

    以前学过Haskell,前几天又复习了其中的部分内容. 函数式编程与命令式编程有着不一样的地方,函数式编程中函数是第一等公民,通过使用少量的几个数据结构如list.map.set,以及在这些数据结构上 ...

最新文章

  1. 2020年最畅销的20款电动汽车,特斯拉和五菱你偏向谁?
  2. Kettle使用_19 HTTP Client与XML JavaSript解析
  3. windows系统-程序加载时生成栈和堆的过程
  4. 如果没准备这些面试题,找工作还是缓一缓吧
  5. 深入理解Java中的反射技术
  6. python turtle 画数字8_turtle库的常用方法
  7. linux抹掉所有分区,找到了linux分区顺序错乱修复方法
  8. iQOO手机正式发布,全新性能旗舰打造爆燃体验
  9. 【Elasticsearch】Elasticsearch中的相似度评分介绍
  10. mysql 读未提交数据,MySql数据库的事务隔离级别学习
  11. 冰雪经济下,全民滑雪进入国际化的“黄金时代”
  12. shell编程阶段性总结+几个shell脚本实例
  13. 基于ESP32CAM的物联网相机系统⑧(用原生JavaWeb实现双摄像头WIFI图传)
  14. Python-基于request豆瓣电影票房信息爬取,简单粗暴
  15. 今天跟好朋友的一段超长爆笑聊天记录(Space搬家)
  16. 图解HTTP+彩色版 pdf版学习(更新中)
  17. 国外知名音视频领域的科技公司
  18. AKG K420 耳机线的维修
  19. jdk动态代理,cglib代理
  20. 风控标签体系的使用与介绍

热门文章

  1. 15.三数之和-LeetCode
  2. mysql 数据库连接不够_一个Web报表项目的性能分析和优化实践(二):MySQL数据库连接不够用(TooManyConnections)问题的一次分析和解决案例...
  3. 阿诺德图像加密c语言,基于Arnold变换的数字图像加密算法
  4. Windows 10 修改网络名字
  5. DataGrip快捷键(执行SQL、格式化SQL)
  6. 微信 html关闭当前页
  7. AndroidStuido连接不上手机的解决方法
  8. [原创]FOCUS处理系统流程之:大文本文件极速合并(sps文件合并)
  9. 智能一代云平台(三):15年上半年维护总结
  10. 枪口对准Google无人车