当前位置: 首页 > news >正文

佛山做网站建设/南宁网站推广公司

佛山做网站建设,南宁网站推广公司,游戏网站开发,做移动类网站的书推荐概述: 函数式接口:有且仅有一个抽象方法的接口Java中函数式编程体现就是Lambda表达式,所以函数式接口就是可以适用Lambda使用的接口,只有确保接口中有且仅有一个抽象方法,Java中的Lambda才能顺利地进行推导不清楚Lambd…

概述:

  • 函数式接口:有且仅有一个抽象方法的接口
  • Java中函数式编程体现就是Lambda表达式,所以函数式接口就是可以适用Lambda使用的接口,只有确保接口中有且仅有一个抽象方法,Java中的Lambda才能顺利地进行推导
  • 不清楚Lambda表达式的可以看这个

我们先看一个例子,demo

Interface1:接口1

Demo:示例demo 

package com.testFunctionalInterface;/*** @author 林高禄* @create 2020-06-03-15:31*/
public class Demo {public static void main(String[] args) {useInterface1("林高禄",s-> System.out.println(s));}private static void useInterface1(String s,Interface1 i){i.method(s);}
}interface Interface1{void method(String s);
}

运行输出:

林高禄

接口Interface1,只有一个抽象方法,并且能用Lambda表达式体现,那么我们就说接口Interface1是函数式接口,那么有什么标志能体现Interface1是函数式接口呢,如果别人不知道,在Interface1里面再加一个抽象方法,那么Interface1不会报错,但是使用的Lambda就会报错了,所以我们要用一个标志标明这个接口就是函数式接口,不能在加其他的抽象方法了,这个标志就是

@FunctionalInterface

如何检测一个接口是不是函数式接口呢?

  • @FunctionalInterface
  • 放在接口定义的上方:如果接口是函数式接口,编译通过;如果不是,编译失败
  • 加了@FunctionalInterface的接口,有且仅有一个抽象方法,才编译通过。

那么我们的示例修改后的代码为

package com.testFunctionalInterface;/*** @author 林高禄* @create 2020-06-03-15:31*/
public class Demo {public static void main(String[] args) {useInterface1("林高禄",s-> System.out.println(s));}private static void useInterface1(String s,Interface1 i){i.method(s);}
}@FunctionalInterface
interface Interface1{void method(String s);
}

函数式接口作为参数

 接口Runnable就是函数式接口,把它作为参数传入线程中启动

 

package com.testFunctionalInterface;/*** @author 林高禄* @create 2020-06-03-15:44*/
public class Demo1 {public static void main(String[] args) {// 匿名内部类new Thread(new Runnable() {@Overridepublic void run() {System.out.println("线程"+Thread.currentThread().getName()+"启动了!");}}).start();// Lambda表达式new Thread(()-> System.out.println("线程"+Thread.currentThread().getName()+"启动了!")).start();Runnable runnable = () -> System.out.println("线程" + Thread.currentThread().getName() + "启动了!");new Thread(runnable).start();}
}

运行输出:

线程Thread-0启动了!
线程Thread-1启动了!
线程Thread-2启动了!

函数式接口作为返回值

Comparator就是函数式接口

按学生的年龄排序

  • 排序前打印
  • 学生类实现Comparable接口,重写排序方法compareTo进行年龄排序后打印
  • 自写获取排序进行年龄排序后打印
  • 自写获取排序进行颜值排序后打印
package com.testFunctionalInterface;import java.util.*;/*** @author 林高禄* @create 2020-06-03-15:56*/
public class Demo2 {public static void main(String[] args) {List<Student> list = new ArrayList<>();Student s1 = new Student("林高禄",27,90);Student s2 = new Student("吴忠威",31,99);Student s3 = new Student("徐辉强",25,97);list.add(s1);list.add(s2);list.add(s3);System.out.println("排序前"+list);Collections.sort(list);System.out.println("类自排序,年龄排序后"+list);Collections.sort(list,getComparator());System.out.println("获取返回值排序,年龄排序后"+list);Collections.sort(list,(student1,student2)->student2.getYanzhi()-student1.getYanzhi());System.out.println("获取返回值排序,颜值排序后"+list);}private static Comparator<Student>  getComparator(){// 匿名内部类/* return new Comparator<Student>() {@Overridepublic int compare(Student s1,Student s2) {return s2.getAge()-s1.getAge();}};*/// Lambda表达式return (s1,s2)->s2.getAge()-s1.getAge();}
}
class Student implements Comparable<Student>{@Overridepublic int compareTo(Student s) {return this.getAge()-s.getAge();}private String name;private int  age;private int yanzhi;public Student(String name, int age, int yanzhi) {this.name = name;this.age = age;this.yanzhi = yanzhi;}public String getName() {return name;}public void setName(String name) {this.name = name;}public int getAge() {return age;}public void setAge(int age) {this.age = age;}public int getYanzhi() {return yanzhi;}public void setYanzhi(int yanzhi) {this.yanzhi = yanzhi;}@Overridepublic String toString() {return "Student{" +"name='" + name + '\'' +", age=" + age +", yanzhi=" + yanzhi +'}';}
}

运行输出:

排序前[Student{name='林高禄', age=27, yanzhi=90}, Student{name='吴忠威', age=31, yanzhi=99}, Student{name='徐辉强', age=25, yanzhi=97}]
类自排序,年龄排序后[Student{name='徐辉强', age=25, yanzhi=97}, Student{name='林高禄', age=27, yanzhi=90}, Student{name='吴忠威', age=31, yanzhi=99}]
获取返回值排序,年龄排序后[Student{name='吴忠威', age=31, yanzhi=99}, Student{name='林高禄', age=27, yanzhi=90}, Student{name='徐辉强', age=25, yanzhi=97}]
获取返回值排序,颜值排序后[Student{name='吴忠威', age=31, yanzhi=99}, Student{name='徐辉强', age=25, yanzhi=97}, Student{name='林高禄', age=27, yanzhi=90}]

从最后一个排序看出,我们用Lambda表达式写排序简直就是太方便了

常用的函数式接口(Java8)

  • Supplier接口(供给型)
  • Consumer接口(消费型)
  • Predicate接口(谓词型)
  • Function接口(功能型)

我们用学生类来做例子,学生类Student主要有姓名,年龄 

package com.testFunctionalInterface;/*** @author 林高禄* @create 2020-06-04-9:11*/
public class Student {private String name;private int age;public Student(String name, int age) {this.name = name;this.age = age;}public String getName() {return name;}public void setName(String name) {this.name = name;}public int getAge() {return age;}public void setAge(int age) {this.age = age;}@Overridepublic String toString() {return "Student{" +"name='" + name + '\'' +", age=" + age +'}';}
}

 

Supplier接口(供给型)

Supplier<T>:包含一个无参的方法

  • T get():获得结果
  • 该方法不需要参数,它会按照某种实现逻辑(由Lambda表达式实现)返回一个数据
  • Supplier<T>接口也被称为生产型接口,如果我们指定了接口的泛型是什么类型,那么接口中的get方法就会生产什么类型的数据供我们使用

例子1:获取年龄大于等于28岁的第一个学生

package com.testFunctionalInterface;import java.util.ArrayList;
import java.util.List;
import java.util.function.Supplier;/*** @author 林高禄* @create 2020-06-04-9:08*/
public class SupplierDemo1 {public static void main(String[] args) {Student s1 = new Student("林高禄",27);Student s2 = new Student("吴忠威",31);Student s3 = new Student("徐辉强",28);List<Student> list = new ArrayList<>();list.add(s1);list.add(s2);list.add(s3);// Lambda表达式获取Supplier对象Supplier<Student> supplier = ()->{Student returnStudent = null;for(Student s:list){if(s.getAge()>=28){returnStudent =  s;break;}}return returnStudent;};// 直接获取System.out.println(supplier.get().toString());System.out.println("----------------------------");// 传入方法获取Student student = getStudent(supplier);System.out.println(student.toString());}private static Student getStudent(Supplier<Student> s){return s.get();}
}

运行输出:

Student{name='吴忠威', age=31}
----------------------------
Student{name='吴忠威', age=31}

例子2:获取随机数,分别用匿名内部类,Lambda表达式和方法引用获取

package com.testFunctionalInterface;import java.util.Random;
import java.util.function.Supplier;/*** @author 林高禄* @create 2020-06-04-9:20*/
public class SupplierDemo2 {public static void main(String[] args) {// 匿名内部类Supplier<Integer> supplier = new Supplier<Integer>() {@Overridepublic Integer get() {return new Random().nextInt();}};System.out.println(supplier.get());System.out.println("-------------------------------");// Lambda表达式supplier = () -> new Random().nextInt();System.out.println(supplier.get());System.out.println("-------------------------------");// 方法引用Supplier<Random> supplier2 = Random::new;System.out.println(supplier2.get().nextInt());}}

运行输出:

-729626870
-------------------------------
809183650
-------------------------------
-803077133 

Consumer接口(消费型)

Consumer<T>:包含两个方法

  • void accept(T t):对给定的参数执行操作
  • default Consumer<T> addThen(Consumer after):返回一个组合的Consumer,依次执行此操作,然后执行after操作
  • Consumer<T>接口也被称为消费型接口,它消费的数据的数据类型由泛型决定

例子1:消费一个学生,并且输出学生的名字,反转再输出一次

代码说明:

  • 匿名内部类消费
  • Lambda表达式消费
  • 方法引用1消费
  • 方法引用2消费
  • 调用方法1消费
  • 调用方法2消费
package com.testFunctionalInterface;import java.util.function.Consumer;/*** @author 林高禄* @create 2020-06-04-9:08*/
public class ConsumerDemo1 {public static void main(String[] args) {Student s1 = new Student("林高禄",27);// 匿名内部类System.out.println("------------匿名内部类-------------");Consumer<Student> consumer = new Consumer<Student>() {@Overridepublic void accept(Student student) {System.out.println(student.getName());System.out.println(new StringBuilder(student.getName()).reverse());}};consumer.accept(s1);// Lambda表达式System.out.println("------------Lambda表达式-------------");consumer = s-> System.out.println(s.getName()+"\n"+new StringBuilder(s.getName()).reverse());consumer.accept(s1);// 方法引用1System.out.println("------------方法引用1-------------");Consumer<String> consumer2 = System.out::println;consumer2.accept(s1.getName()+"\n"+new StringBuilder(s1.getName()).reverse());// 方法引用2System.out.println("-------------方法引用2------------");consumer = ConsumerDemo1::printStudentName;consumer.accept(s1);// 调用方法1System.out.println("-------------调用方法1------------");printStudentName(s1,s-> System.out.println(s.getName()),s-> System.out.println(new StringBuilder(s.getName()).reverse()));// 调用方法2System.out.println("-------------调用方法2------------");printStudentName2(s1,s-> System.out.println(s.getName()),s-> System.out.println(new StringBuilder(s.getName()).reverse()));}private static void printStudentName(Student s){System.out.println(s.getName()+"\n"+new StringBuilder(s.getName()).reverse());}private static void printStudentName(Student s,Consumer<Student> consumer1,Consumer<Student> consumer2){consumer1.accept(s);consumer2.accept(s);}private static void printStudentName2(Student s,Consumer<Student> consumer1,Consumer<Student> consumer2){consumer1.andThen(consumer2).accept(s);}
}

运行输出:

------------匿名内部类-------------
林高禄
禄高林
------------Lambda表达式-------------
林高禄
禄高林
------------方法引用1-------------
林高禄
禄高林
-------------方法引用2------------
林高禄
禄高林
-------------调用方法1------------
林高禄
禄高林
-------------调用方法2------------
林高禄
禄高林

Predicate接口(谓词型)

Predicate<T>:常用的四个方法

  • boolean test(T t):对给定的参数进行判断(判断逻辑由Lambda表达式实现),返回一个布尔值
  • default Predicate<T> negate():返回一个逻辑的否定,对应逻辑非
  • default Predicate<T> and(Predicate other):返回一个组合判断,对应短语与
  • default Predicate<T> or(Predicate other):返回一个组合判断,对应短语或
  • Predicate<T> 接口通常用于判断参数是否满足指定的条件,起判断作用

例子,判断学生是否满足各种条件

package com.testFunctionalInterface;import java.util.function.Predicate;/*** @author 林高禄* @create 2020-06-04-11:07*/
public class PredicateDemo {public static void main(String[] args) {Student student = new Student("林高禄",27);System.out.println("学生信息:"+student);// 判断学生是否姓名是否以"林"字开头System.out.println("判断学生是否姓名是否以\"林\"字开头");Predicate<Student> predicate = s->s.getName().startsWith("林");System.out.println(predicate.test(student));// 判断学生是否超过30岁System.out.println("判断学生是否超过30岁");predicate = new Predicate<Student>() {@Overridepublic boolean test(Student student) {return student.getAge()>30;}};System.out.println(predicate.test(student));// 判断学生是否小于等于30岁System.out.println("判断学生是否小于等于30岁");// 这里用了negate(),返回一个逻辑的否定,对应逻辑非,所以输出是trueSystem.out.println(predicate.negate().test(student));// 判断学生是否以"林"字开头,或者超过30岁System.out.println("判断学生是否以\"林\"字开头,或者超过30岁");predicate = s->s.getName().startsWith("林");Predicate<Student> predicate2 = s->s.getAge()>30;System.out.println(predicate.or(predicate2).test(student));// 判断学生是否以"林"字开头,并且超过30岁System.out.println("判断学生是否以\"林\"字开头,并且超过30岁");System.out.println(predicate.and(predicate2).test(student));}
}

运行输出:

学生信息:Student{name='林高禄', age=27}
判断学生是否姓名是否以"林"字开头
true
判断学生是否超过30岁
false
判断学生是否小于等于30岁
true
判断学生是否以"林"字开头,或者超过30岁
true
判断学生是否以"林"字开头,并且超过30岁
false

Function接口(功能型)

Function<T,R>:常用的两个方法

  • R apply(T t):将此函数应用于给定的参数
  • default<V> Function andThen(Functiona after):返回一个函数组合,首先将该函数应用于输入,然后将after函数应用于结果
  • default<V> Function compose(Functiona before):返回一个函数组合,首先将before函数应用于输入,然后将此函数应用于结果

例子:处理学生类

package com.testFunctionalInterface;import java.util.function.Function;/*** @author 林高禄* @create 2020-06-04-11:34*/
public class FunctionDemo {public static void main(String[] args) {Student student = new Student("林高禄",27);// 求出学生的姓名长度Function<Student,Integer> function = s->s.getName().length();System.out.println(function.apply(student));// 把学生的姓名后面加上"**"Function<Student,String> function2 = Student::getName;Function<String,String> function3 = s->s+"**";System.out.println(function2.andThen(function3).apply(student));//注意比较和上面的区别,一前一后System.out.println(function3.compose(function2).apply(student));}
}

运行输出:

3
林高禄**
林高禄**

注意andThen和compose的顺序,到这里常用的函数式接口就介绍完了

函数式接口的进阶用法,Stream流

http://www.lbrq.cn/news/773461.html

相关文章:

  • 仿做购物网站/灰色词seo推广
  • 做网站用哪几个端口 比较好/b站推广网站入口2023的推广形式
  • 广告投放跟网站建设一样吗/成人营销管理培训班
  • 优设网设计服务平台/厦门seo优
  • 盘古网建站/网推接单平台
  • 网上给别人做网站/宁波seo网络推广优化价格
  • 上海企业网站建设靠谱/中国新冠疫苗接种率
  • 织梦网站主页/企业文化标语经典
  • 泰州网站建设设计/影视后期培训班一般要多少钱
  • 在家做的打字兼职的网站/抖音搜索引擎推广
  • 网站开发基础与提高/查看别人网站的访问量
  • 做毕设好的网站/竞价排名
  • 域名停靠网站免费进入/山东seo首页关键词优化
  • 国外做外挂的网站/百度竞价
  • 网站开发与兼容模式/网站搜什么关键词
  • 独立网站商城建设/信息流广告案例
  • 做网站人/seo实战论坛
  • 百度关键词购买/seo是什么工作内容
  • 香港做批发的网站有哪些/百度视频seo
  • win7如何安装iis来浏览asp网站/广州灰色优化网络公司
  • 大学生帮别人做网站/推广网站公司
  • 网站开发 外包 哪家/北京网站制作设计
  • 淄博网站建设相关文章/营销型网站有哪些平台
  • 外贸网站设计制作/域名seo站长工具
  • 如何做设计网站页面/黄山seo推广
  • 网站建设的违约责任/专业seo网络营销公司
  • 深圳企业网站定制公司/厦门人才网个人会员登录
  • 网站开发流程分析/网站关键词优化怎么做的
  • 大连网站建设仟亿科技/二级域名查询网站
  • 浦东网站建设公司/阿里指数app下载
  • 机器学习-Cluster
  • 微软正式将GPT-5接入Microsoft Copilot Studio(国际版)
  • Baumer高防护相机如何通过YoloV8深度学习模型实现纸箱的实时检测计数(C#代码UI界面版)
  • 云计算分类与主流产品
  • 开博尔DA5耳放小尾巴体验评测:实体按键给到位,便携HiFi上手挺好用的
  • C# 异步编程(BeginInvoke和EndInvoke)