Java 关于函数式接口与Lambda表达式之间的关系
java是一种面向对象的语言,java中的一切都是对象,即数组,每个类创建的实例也是对象。在java中定义的函数或方法不可能完全独立,也不能将方法函数作为参数或返回值给实例。
在java7及以前,我们一直都是通过匿名内部类把方法或函数当做参数传递,如下是一个线程实例。
@Test public void testAnonymous() { new Thread(new Runnable() { @Override public void run() { System.out.println("匿名内部类"); } }).start(); }
输出结果为:“匿名内部类”
而在java8之后增加了一种语言特性,Lambda表达式。Lambda表达式为Java添加了缺失的函数式编程特点。而Lambda表达式是对象,它依赖于一个特别的类型-----函数式接口。
Lambda表达式语法:()- > {}
接下来让我们了解一下 Lambda 表达式的结构。
一个Lambda表达式可以有零个或多个参数;
参数的类型既可以明确声明,也可以根据上下文来推断。例如:(int a)与(a)效果相同;
所有参数需包含在圆括号内,参数之间用逗号相隔。例如:(a, b) 或 (int a, int b) 或 (String a, int b, float c);
空圆括号代表参数集为空。例如:() -> 42;
当只有一个参数,且其类型可推导时,圆括号()可省略。例如:a -> return a*a;
Lambda表达式的主体可包含零条或多条语句;
如果Lambda表达式的主体只有一条语句,花括号{}可省略。匿名函数的返回类型与该主体表达式一致;
如果Lambda表达式的主体包含一条以上语句,则表达式必须包含在花括号{}中(形成代码块)。匿名函数的返回类型与代码块的返回类型一致,若没有返回则为空。
简单介绍完Lambda表达式,接下来介绍一下函数式接口
什么是函数式接口:
有且仅有一个抽象方法的接口称作函数式接口
例如:上述的Runnable就是一种函数式接口,其内部只有一个run方法
其中注解@FunctionalInterface 就是标注此接口为函数式接口的注释,当你接口不是函数式接口的时候,这个注解会帮你显式的表达出编译层面的错误,用以提示该接口不是函数式接口,如图:郑州人流医院哪家好 http://mobile.sgyy029.com/
上述线程代码可以更改为:
@Testpublic void testAnonymous() { new Thread(() -> System.out.println("匿名内部类")).start();}
输出结果:“匿名内部类”
可以简单理解为,我们为run方法写了一个实现类,而run方法是无参的,所以()->
根据Lambda表达式特性,body中只有一条语句,我们可以省略{ }
所以最后结果为()-> System.out.println("匿名内部类").start( );
使用Lambda表达式的方法不止一种。在下面的例子中,我们先是用常用的箭头语法创建Lambda表达式,之后,使用Java 8全新的双冒号(::)操作符将一个常规方法转化为Lambda表达式:
@Test public void testAnonymous() { //传统for循环 List list = Arrays.asList(1, 2, 3); for (Integer a : list) { System.out.println(a); }
//Lambda版-箭头语法 list.forEach(a -> System.out.println(a));
//Lambda版-双冒号语法 list.forEach(System.out::println); }
三种运算方式输出结果一样,我们点进去看看forEach底层实现,看看forEach是如何实现的
可以看到forEach()中需要的不是常规的参数,而是Consumer这个类型的参数,继续点进去看看Consumer是个什么类型
原来forEarch中的参数,是一个函数类型的,而他的抽象方法是一个T泛型,也就是说我们在用forEach的时候需要指定一个类型
所以forEarch写法为 forEach(类型 - > 实现 )
java8新推出的数据流中的map也是同样的原理,有兴趣的小伙伴自行测试。
Java 关于函数式接口与Lambda表达式之间的关系的更多相关文章
- Java函数式接口与Lambda表达式
什么是函数式接口? 函数式接口是一种特殊的接口,接口中只有一个抽象方法. 函数式接口与Lambda表达式有什么关系? 当需要一个函数式接口的对象时,可以提供一个lambda表达式. package l ...
- Java函数式编程:一、函数式接口,lambda表达式和方法引用
Java函数式编程 什么是函数式编程 通过整合现有代码来产生新的功能,而不是从零开始编写所有内容,由此我们会得到更加可靠的代码,并获得更高的效率 我们可以这样理解:面向对象编程抽象数据,函数式编程抽象 ...
- Lambda01 编程范式、lambda表达式与匿名内部类、函数式接口、lambda表达式的写法
1 编程范式 主要的编程范式有三种:命令式编程,声明式编程和函数式编程. 1.1 命令式编程 关注计算机执行的步骤,就是告诉计算机先做什么后做什么 1.2 声明式编程 表达程序的执行逻辑,就是告诉计算 ...
- java反射-Method中的invoke方法的用法-以及函数式接口和lambda表达式
作者最近研究框架底层代码过程中感觉自己基础不太牢固,于是写了一点案例,以防日后忘记 接口类:Animals 1 public interface Animals { 2 3 public void e ...
- 函数式接口和Lambda表达式
函数式接口(一般标有@FunctionalInterface)就是只定义一个抽象方法的接口. 一个接口,如果满足函数式接口的定义,那么即使不标注为 @FunctionalInterface, 编译器依 ...
- Java8 学习笔记--函数式接口与lambda表达式的关系
在java中,lambda表达式与函数式接口是不可分割的,都是结合起来使用的. 对于函数式接口,我们可以理解为只有一个抽象方法的接口,除此之外它和别的接口相比并没有什么特殊的地方.为了确保函数式接口的 ...
- Java8函数式接口和Lambda表达式
两者关系: Lambda表达式就是函数式接口(FunctionalInterface)实现的快捷方式,它相当于函数式接口实现的实例,因为在方法中可以使用Object作为参数,所以把Lambda表达式作 ...
- Java8函数式接口以及lambda表达式实践
罗列一下遇到可以转换成lamada表达式的场景,仅供参考,如有更好的方式,欢迎在评论区留言. 1.计算订单总金额 订单总金额一般是在后台循环叠加每个购买商品的金额已获取到,通常的方式如下 BigDec ...
- Java 函数式编程(Lambda表达式)与Stream API
1 函数式编程 函数式编程(Functional Programming)是编程范式的一种.最常见的编程范式是命令式编程(Impera Programming),比如面向过程.面向对象编程都属于命令式 ...
随机推荐
- 201871010123-吴丽丽 《面向对象程序设计(Java)》第八周学习总结
201871010123-吴丽丽<面向对象程序设计(Java)>第八周学习总结 项目 内容 这个作业属于哪个课程 http://www.cnblogs.com/nwnu-daizh/ ...
- day7_7.5 字符表与文件操作
一.字符编码. 1. 在计算机的运行中,有三大部分组成,计算机硬件,操作系统,应用程序,当使用者在使用文档编写文字时,所显示的所有字符都存储在内存中,随后再存储在硬盘里,(仅限文字),所以,当美国人发 ...
- Shell 脚本中 '$' 符号的多种用法
通常情况下,在工作中用的最多的有如下几项: $0:Shell 的命令本身 $1 到 $9:表示 Shell 的第几个参数 $? :显示最后命令的执行情况 $#:传递到脚本的参数个数 $$:脚本运行的当 ...
- VIJOS-P1064 迎春舞会之数字舞蹈
洛谷 P1538 迎春舞会之数字舞蹈 洛谷传送门 JDOJ 1245: VIJOS-P1064 迎春舞会之数字舞蹈 JDOJ传送门 Description 在越来越讲究合作的时代,人们注意的更多的 ...
- JAVA并归排序(数组+链表)
并归排序与快速排序相似,靠分治思想突破了排序算法 O(n2) 的瓶颈. 我们看回顾一下几大排序算法的时间.空间复杂度: 排序算法 平均时间复杂度 最坏时间复杂度 空间复杂度 是否稳定 冒泡排序 O(n ...
- map的基本操作
向map添加元素: 因为map是不允许出现重复关键字的,所以如果重复插入键相同的元素后面的元素是不会插入成功的,下面是一个验证程序: #include<iostream> #include ...
- [TJOI2019]唱,跳,rap,篮球(生成函数,组合数学,NTT)
算是补了个万年大坑了吧. 根据 wwj 的题解(最准确),设一个方案 \(S\)(不一定合法)的鸡你太美组数为 \(w(S)\). 答案就是 \(\sum\limits_{S}[w(S)=0]\). ...
- Linux性能优化实战学习笔记:第十七讲
一.缓存命中率 1.引子 1.我们想利用缓存来提升程序的运行效率,应该怎么评估这个效果呢? 用衡量缓存好坏的指标 2.有没有哪个指标可以衡量缓存使用的好坏呢? 缓存命中率 3.什么是缓存命中率? 所谓 ...
- [LeetCode] 436. Find Right Interval 找右区间
Given a set of intervals, for each of the interval i, check if there exists an interval j whose star ...
- [LeetCode] 50. Pow(x, n) 求x的n次方
Implement pow(x, n), which calculates x raised to the power n(xn). Example 1: Input: 2.00000, 10 Out ...