Day-24

Lambda表达式、函数式接口

1        Lambda

1.1        概述

Lambda表达式是一种没有名字的函数,也可称为闭包,是Java 8 发布的最重要新特性。

本质上是一段匿名内部类,也可以是一段可以传递的代码。

还有叫箭头函数的...

1.2        为什么要使用Lambda表达式

Lambda表达式就是一个匿名内部类的简写方式

使程序更加简洁清晰,编程效率也得到了提高

1.3        和匿名内部类对比

更加简介清晰

1.4        语法结构

可选类型声明:不需要声明参数类型,编译器可以统一识别参数值。

                   

可选的参数圆括号:一个参数无需定义圆括号,但多个参数需要定义圆括号。

                   

可选的大括号:如果主体包含了一个语句,就不需要使用大括号。

如果不写{}  return 不能写  分号不能写

                   

可选的返回关键字:如果主体只有一个表达式返回值则编译器会自动返回值,大括号需要指定明表达式返回了一个数值

     如果只有一条语句,并且是返回值语句,就可以不写return 不写 {} 

        如果写上{}  就必须写return 和 ;

    如果有 多条语句,必须写{}  return 和 ;  也必须写

1.5        案例

1 不需要参数,返回值为5

()-> 5

2 接收一个参数(数字类型),返回其2倍的值 

x -> x*2

3 接受2个参数(数字),并返回他们的差值 

(x,y)-> x-y

1.6        练习

 

  2        函数式接口

 2.1        介绍

英文称为Functional Interface

         

其本质是一个有且仅有一个抽象方法,但是可以有多个非抽象方法的接口。

         

核心目标是为了给Lambda表达式的使用提供更好的支持,进一步达到函数式编程的目标,可通过运用函数式编程极大地提高编程效率。

         

其可以被隐式转换为 lambda 表达式。

2.2        特点

函数式接口是仅制定一个抽象方法的接口

可以包含一个或多个静态或默认方法

专用注解即@FunctionalInterface 检查它是否是一个函数式接口,也可不添加该注解

如果有两个或以上 抽象方法,就不能当成函数式接口去使用,也不能添加@FunctionalInterface这个注解

如果只有一个抽象方法,那么@FunctionalInterface注解 加不加 都可以当做函数式接口去使用

 2.3        代码实现

2.3.1        无参情况

public class FunInterface_01 {

    // 自定义静态方法,接收接口对象

    public static void call(MyFunctionInter func) {

        // 调用接口内的成员方法

        func.printMessage();

    }

    public static void main(String[] args) {

        // 第一种调用 : 直接调用自定义call方法,传入函数

        FunInterface_01.call(() -> {

            System.out.println("HelloWorld!!!");

        });

        // 第二种调用 : 先创建函数对象,类似于实现接口的内部类对象

        MyFunctionInter inter = () -> {

            System.out.println("HelloWorld2!!!!");

        };

        // 调用这个实现的方法

        inter.printMessage();

    }

}

// 函数式接口

@FunctionalInterface

interface MyFunctionInter {

    void printMessage();

}

演示示例:_01_FunInterface.java

2.3.2        有参情况

public class FunInterface_02 {

    // 自定义静态方法,接收接口对象

    public static void call(MyFunctionInter_02 func, String message) {

        // 调用接口内的成员方法

        func.printMessage(message);

    }

    public static void main(String[] args) {

        // 调用需要传递的数据

        String message = "有参函数式接口调用!!!";

        // 第一种调用 : 直接调用自定义call方法,传入函数,并传入数据

        FunInterface_02.call((str) -> {

            System.out.println(str);

        }, message);

        // 第二种调用 : 先创建函数对象,类似于实现接口的内部类对象

        MyFunctionInter_02 inter = (str) -> {

            System.out.println(str);

        };

        // 调用这个实现的方法

        inter.printMessage(message);

    }

}

// 函数式接口

@FunctionalInterface

interface MyFunctionInter_02 {

    void printMessage(String message);

}

演示示例:_02_FunInterface.java

2.4        JDK自带常用的函数式接口

2.4.1         Supplier<T>接口

Supplier<T>接口    代表结果供应商,所以有返回值,可以获取数据

有一个get方法,用于获取数据

public class _03_JdkOwn_01 {

    private static String getResult(Supplier<String> function) {

        return function.get();

    }

    public static void main(String[] args) {

        // 1

        String before = "张三";

        String after = "你好";

        // 把两个字符串拼接起来

        System.out.println(getResult(() -> before + after));

        // 2 //创建Supplier容器,声明为_03_JdkOwn类型

        // 此时并不会调用对象的构造方法,即不会创建对象

        Supplier<_03_JdkOwn_01> sup = _03_JdkOwn_01::new;

        _03_JdkOwn_01 jo1 = sup.get();

        _03_JdkOwn_01 jo2 = sup.get();

    }

    public _03_JdkOwn_01() {

        System.out.println("构造方法执行了");

    }

}

演示示例:_03_JdkOwn_01.java

2.4.2        Consumer<T>接口

Consumer<T>接口    消费者接口所以不需要返回值

有一个accept(T)方法,用于执行消费操作,可以对给定的参数T 做任意操作

public class _04_JdkOwn_02 {

    private static void consumeResult(Consumer<String> function, String message) {

        function.accept(message);

    }

    public static void main(String[] args) {

        // 传递的参数

        String message = "消费一些内容!!!";

        // 调用方法

        consumeResult(result -> {

            System.out.println(result);

        }, message);

    }

}

演示示例:_04_JdkOwn_02.java

2.4.3         Function<T,R>接口

Function<T,R>接口  表示接收一个参数并产生结果的函数

顾名思义,是函数操作的

有一个R apply(T)方法,Function中没有具体的操作,具体的操作需要我们去为它指定,因此apply具体返回的结果取决于传入的lambda表达式

public class _05_JdkOwn_03 {

    // Function<参数, 返回值>

    public static void convertType(Function<String, Integer> function,

            String str) {

        int num = function.apply(str);

        System.out.println(num);

    }

    public static void main(String[] args) {

        // 传递的参数

        String str = "123";

        // s是说明需要传递参数, 也可以写 (s)

        convertType(s -> {

            int sInt = Integer.parseInt(s);

            return sInt;

        }, str);

    }

}

演示示例:_05_JdkOwn_03.java

2.4.4        ​​​​​​​Predicate<T>接口

Predicate<T>接口   断言接口

就是做一些判断,返回值为boolean

有一个boolean test(T)方法,用于校验传入数据是否符合判断条件,返回boolean类型

public class _06_JdkOwn_04 {

    // 自定义方法,并且 Predicate 接收String字符串类型

    public static void call(Predicate<String> predicate, String isOKMessage) {

        boolean isOK = predicate.test(isOKMessage);

        System.out.println("isOK吗:" + isOK);

    }

    public static void main(String[] args) {

        // 传入的参数

        String input = "ok";

        call((String message) -> {

            // 不区分大小写比较,是ok就返回true,否则返回false

            if (message.equalsIgnoreCase("ok")) {

               return true;

            }

            return false;

        }, input);

    }

}

3        方法引用和构造器调用​​​​​​​

3.1        对象调用成员\

3.2        类名调用静态

 

3.3        类名调用成员

 

3.4        构造方法调用

 

3.5        数组引用

 

4        Stream API

4.1        概念说明

数据渠道、管道,用于操作数据源(集合、数组等)所生成的元素序列。         

集合讲的是数据,流讲的是计算        即一组用来处理数组,集合的API。

4.2        特点

Stream 不是数据结构,没有内部存储,自己不会存储元素。             

Stream 不会改变源对象。相反,他们会返回一个持有结果的新Stream。            

Stream 操作是延迟执行的。这意味着他们会等到需要结果的时候才执行。              

不支持索引访问。                

延迟计算             

支持并行                

很容易生成数据或集合          

支持过滤,查找,转换,汇总,聚合等操作。

 

4.3        应用场景

流式计算处理,需要延迟计算、更方便的并行计算

更灵活、简洁的集合处理方式场景

4.4        代码实现

4.4.1        运行机制

Stream分为源source,中间操作,终止操作。            

流的源可以是一个数组,集合,生成器方法,I/O通道等等。          

一个流可以有零个或多个中间操作,每一个中间操作都会返回一个新的流,供下一个操作使用,一个流只会有一个终止操作。 

中间操作也称为转换算子-transformation           

Stream只有遇到终止操作,它的数据源会开始执行遍历操作。         

终止操作也称为动作算子-action

因为动作算子的返回值不再是 stream,所以这个计算就终止了

只有碰到动作算子的时候,才会真正的计算

4.4.2        创建流的方式

 

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值