2021-03-30:java第28天:函数式接口用Lambda表达式简化:Supplier,Consumer,Predicate,Function四个常用函数式接口及内部方法介绍

1.函数式接口

这样的接口也同时可以用Lambda表达式简化

package Part3.Day_28;
/*
    函数式接口:有且只有一个抽象方法的接口,称之为函数式接口
    接口中可以包含其他的方法(默认,静态,私有)
 */
@FunctionalInterface //函数式接口,这个注解可以检测这个接口是否是函数式接口
//1.接口中没有抽象方法 2.抽象方法多于一个
public interface MyFunctionalInterface {
    public  abstract void method();

}


package Part3.Day_28;

public class MyFunctionalInterfaceImpl implements MyFunctionalInterface {
    @Override
    public void method() {

    }
}


package Part3.Day_28;
/*
    函数式接口的使用:一般可以作为方法的参数和返回值类型

 */
public class demo {
    //定义一个方法,参数使用函数式接口MyFunctionalInterface
    public static void show(MyFunctionalInterface myInter){
        myInter.method();
    }

    public static void main(String[] args) {
        //调用show方法,方法参数是一个接口,传递接口的实现类
        show(new MyFunctionalInterfaceImpl());

        //调用show,传递接口的匿名内部类,匿名内部类是会自动产生一个类的
        show(new MyFunctionalInterface() {
            @Override
            public void method() {
                System.out.println("使用匿名内部类重写接口中的抽象方法");
            }
        });
        //调用show方法,方法的参数是一个函数式接口,所以我们可以用Lambda表达式,这个不产生类
        show(()->{
            System.out.println("使用Lambda表达式重写接口方法");
        });
    }
}

 

2.Lambda优化日志案例,减少性能浪费

package Part3.Day_28.demo02Lambda;

@FunctionalInterface
public interface MessageBuilder {
    //定义一个拼接消息的抽象方法
    public abstract String builderMessage();
}


package Part3.Day_28.demo02Lambda;
/*
    使用Lambda优化日志案例
    (参数类型,参数)->{方法}
    Lambda特点:延迟加载
    前提:必须存在函数式接口
 */
public class demo02Lambda {
    //定义显示日志方法,传递日志等级和messagebuilder接口
    public static void showLog(int level, MessageBuilder mb){
        //如果是1级则调用MessageBuilder接口中的builderMessage方法
        if(level ==1 ){
            System.out.println(mb.builderMessage());
        }
    }

    public static void main(String[] args) {
        String msg1 = "Hello";
        String msg2 = "World";
        String msg3 = "Java";
        //mb是函数式接口,可以传递Lambda表达式
        showLog(1,()->{
            return msg1+msg2+msg3;
        });
    }
    /*
        使用Lambda表达式作为参数传递,仅仅把参数传到showLog里
        只有满足条件才会调用MessageBuilder中的方法builderMessage
        才会进行字符串的拼接
        如果条件不满足,也就是日志的等级不是1级,
        那么MessageBuilder中的方法builderMessage不会执行,不会存在性能浪费
     */

}

 

3. 函数式接口作为方法的参数案例

package Part3.Day_28.demo02Lambda;
/*
   假设java.lang.Runnable作为一个函数式接口
   假设有一个startThread方法使用该接口作为参数,那么就可以使用Lambda进行传参
   这种情况其实和Thread类的构造方法参数为Runnable一样
 */
public class demo01Runnable {
    public static void startThread(Runnable run){
        //开启多线程
        new Thread(run).start();
    }

    public static void main(String[] args) {
        startThread(new Runnable() {
            @Override
            public void run() {
                System.out.println(Thread.currentThread().getName()+"线程启动了1");
            }
        });
        startThread(()->{
            System.out.println(Thread.currentThread().getName()+"线程启动了2");
        });
        //优化Lambda表达式
        
        startThread(()->
            System.out.println(Thread.currentThread().getName()+"线程启动了3"));
    }
}

输出为:

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

或者:

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

 

4.函数式接口作为方法的返回值类型




package Part3.Day_28.demo03Lambdatest;

import java.util.Arrays;
import java.util.Comparator;

public class demo02Comparator {
    public static Comparator<String> getComparator(){
        /*//方法的返回值是一个接口,我们可以返回这个接口的匿名内部类
        return new Comparator<String>() {
            @Override
            public int compare(String o1, String o2) {
                //按照字符串的降序排序
                return o2.length()-o1.length();
            }
        };*/
        //return (String o1, String o2)->{return o2.length()-o1.length();};
        //省略写法:
        return (o1, o2)-> o2.length()-o1.length();
    }

    public static void main(String[] args) {
        String[] array = {"aaaa","bb","c"};
        //输出排序前数组
        System.out.println(Arrays.toString(array));
        //排序后
        Arrays.sort(array,getComparator());

        System.out.println(Arrays.toString(array));
    }
}

 

5.常用的函数式接口

java.util.function包里

(1). Supplier接口

Supplier接口练习:求数组中元素的最大值

package Part3.Day_28.demo04Supplier;

import java.util.Arrays;
import java.util.function.Supplier;

public class demo02test {
    public static int maxx(Supplier<Integer> function){
        return function.get();
    }

    public static void main(String[] args) {
        int[] arr = {1,2,5,8,9};
        int m = maxx(()->{
            Arrays.sort(arr);
            int max = arr[arr.length-1];
            return max;
        });
        System.out.println(m);

    }
}

(2) Consumer接口 :就是使用这个同类型的数据

字符串反转案例:

package Part3.Day_28.demo04Supplier;

public class test {
    public static void main(String[] args) {
        String a = "赵丽颖";
        System.out.println(new StringBuilder(a).reverse().toString());
        System.out.println(new StringBuffer(a).reverse().toString());

    }

}

Consumer接口还有一个默认方法:

简写:

打印名字练习:

package Part3.Day_28.demo05Consumer;

import java.util.function.Consumer;

public class demo01test {
    public static void main(String[] args) {
        String[] array = {"迪丽热巴,女","古力娜扎,女","马儿扎哈,男"};
        for (String s : array) {
            method(s,(t)-> System.out.print("姓名:"+s.split(",")[0]+" "),
                    (x)-> System.out.println("性别:"+s.split(",")[1]));
        }

    }
    public static void method(String s, Consumer<String> con1,Consumer<String> con2){
        con1.andThen(con2).accept(s);
    }

}

 

(3) Predicate接口

Predicate接口中有三个默认方法

第一个方法:and 相当于与运算符

相当于判断必须两个与,返回结果。方法内部的两个判断条件也是用&&链接起来的

判断一个字符串是否包含某个子字符串:   str.contains("a");

第二个方法: or 相当于 || 符号

第三个方法:negate 相当于取反符号!

集合信息筛选练习:

package Part3.Day_28.demo06Predicate;

import java.util.ArrayList;
import java.util.function.Predicate;

public class demo01test {
    public static void main(String[] args) {
        String[] array = {"迪丽热巴,女","古力娜,女","马儿扎哈,男"};
        ArrayList<String> ans = filter(array,(s)-> s.split(",")[0].length()==4,
                (s)-> s.split(",")[1].equals("女")
        );
        for (String an : ans) {
            System.out.println(an);
        }

    }
    public static ArrayList<String> filter(String[] arr, Predicate<String> p1,Predicate<String> p2){
        ArrayList<String> ans = new ArrayList<>();
        for (String s : arr) {
            boolean x = p1.and(p2).test(s);
            if (x){
                ans.add(s);
            }
        }
        return ans;
    }
}

 

(4) Function接口

 

 

 

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

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值