运用Function接口,简洁的判断并抛出异常

运用Function接口,简洁的判断并抛出异常

学习资料地址:妙用Java 8中的 Function接口 消灭if...else(非常新颖的写法

书读百遍,其义自现

纸上得来终觉浅,绝知此事要躬行

基础

Function函数式接口

使用注解@FunctionalInterface标识,并且只包含一个抽象方法的接口是函数式接口函数式接口主要分为Supplier供给型函数、Consumer消费型函数、Runnable无参无返回型函数和Function有参有返回型函数。

Function可以看作转换型函数

Supplier供给型函数

Supplier的表现形式为不接受参数、只返回数据

package java.util.function;

/**
 * Represents a supplier of results.
 *
 * <p>There is no requirement that a new or distinct result be returned each
 * time the supplier is invoked.
 *
 * <p>This is a <a href="package-summary.html">functional interface</a>
 * whose functional method is {@link #get()}.
 *
 * @param <T> the type of results supplied by this supplier
 *
 * @since 1.8
 */
@FunctionalInterface
public interface Supplier<T> {

    /**
     * Gets a result.
     *
     * @return a result
     */
    T get();
}

Consumer消费型函数

Consumer消费型函数和Supplier刚好相反。Consumer接收一个参数,没有返回值

@FunctionalInterface
public interface Consumer<T> {

    /**
     * Performs this operation on the given argument.
     *
     * @param t the input argument
     */
    void accept(T t);

    /**
     * Returns a composed {@code Consumer} that performs, in sequence, this
     * operation followed by the {@code after} operation. If performing either
     * operation throws an exception, it is relayed to the caller of the
     * composed operation.  If performing this operation throws an exception,
     * the {@code after} operation will not be performed.
     *
     * @param after the operation to perform after this operation
     * @return a composed {@code Consumer} that performs in sequence this
     * operation followed by the {@code after} operation
     * @throws NullPointerException if {@code after} is null
     */
    default Consumer<T> andThen(Consumer<? super T> after) {
        Objects.requireNonNull(after);
        return (T t) -> { accept(t); after.accept(t); };
    }
}

Runnable无参无返回型函数

Runnable的表现形式为即没有参数也没有返回值

@FunctionalInterface
public interface Runnable {
    /**
     * When an object implementing interface <code>Runnable</code> is used
     * to create a thread, starting the thread causes the object's
     * <code>run</code> method to be called in that separately executing
     * thread.
     * <p>
     * The general contract of the method <code>run</code> is that it may
     * take any action whatsoever.
     *
     * @see     java.lang.Thread#run()
     */
    public abstract void run();
}

Function函数的表现形式为接收一个参数,并返回一个值。SupplierConsumerRunnable可以看作Function的一种特殊表现形式

运用

01 处理抛出异常的if(常用)

1 定义函数

定义一个抛出异常的形式的函数式接口, 这个接口只有参数没有返回值是个消费型接口

/**
 * 抛出异常的接口
 * @author : lyn
 * @date : 2022-05-07 21:56
 */
@FunctionalInterface
public interface ThrowExceptionFunction {

    /**
     * 抛出异常
     * @param errorMessage 异常信息
     */
    void throwException(String errorMessage);
}

2 编写判断方法

创建工具类ConciseUtil并创建一个isTure方法,方法的返回值为刚才定义的函数式接口-ThrowExceptionFunctionThrowExceptionFunction的接口实现逻辑为当参数flagtrue时抛出异常

/**
 * 简洁的工具类
 * 简化代码
 *
 * @author : lyn
 * @date : 2022-05-07 21:53
 */
public class ConciseUtil {

    public static ThrowExceptionFunction isTrue(boolean flag) {
        return (errorMessage -> {
            if (flag) {
                throw new RuntimeException(errorMessage);
            }

        });

    }
}

3 使用方式

调用工具类参数参数后,调用函数式接口throwException方法传入异常信息。当出入的参数为false时正常执行

/**
 * @author : lyn
 * @date : 2022-05-07 22:01
 */
public class TestMain {
    public static void main(String[] args) {
        ConciseUtil.isTrue(true).throwException("不能为空");
    }
}

02 处理if分支操作(便于理解源码)

1 定义函数式接口

创建一个名为BranchHandle的函数式接口,接口的参数为两个Runnable接口。这两个两个Runnable接口分别代表了为truefalse时要进行的操作

/**
 * 分支处理接口
 * @author : lyn
 * @date : 2022-05-07 22:35
 */
public interface BranchHandle {

    /**
     * 分支操作
     * @param trueHandle true时执行
     * @param falseHandle false时执行
     */
    void trueOrFalseHandle(Runnable trueHandle,Runnable falseHandle);
}

2 编写判断方法

创建一个名为isTureOrFalse的方法,方法的返回值为刚才定义的函数式接口-BranchHandle

    /**
     * 参数为true或false时,分别进行不同的操作
     * @param flag
     * @return
     */
    public static BranchHandle isTrueOrFalse(boolean flag) {
        return ((trueHandle, falseHandle) -> {
            if (flag){
                trueHandle.run();
            }else{
                falseHandle.run();
            }
        });

    }

3 使用方式

参数为true时,执行trueHandle

ConciseUtil.isTrueOrFalse(false).trueOrFalseHandle(
                ()->{
                    System.out.println("执行true操作");
                },
                ()->{System.out.println("执行false操作");});

03 如果存在值执行消费操作,否则执行基于空的操作

1 定义函数

创建一个名为PresentOrElseHandler的函数式接口,接口的参数一个为Consumer接口。一个为Runnable,分别代表值不为空时执行消费操作和值为空时执行的其他操作

/**
 * 空值与非空值分支处理
 * @author lyn
 */
public interface PresentOrElseHandler<T extends Object> {

    /**
     * 值不为空时执行消费操作
     * 值为空时执行其他的操作
     * 
     * @param action 值不为空时,执行的消费操作
     * @param emptyAction 值为空时,执行的操作
     * @return void    
     **/
   void presentOrElseHandle(Consumer<? super T> action, Runnable emptyAction);
   
}

1 编写判断方法

创建一个名为isBlankOrNoBlank的方法,方法的返回值为刚才定义的函数式接口-PresentOrElseHandler

/**
 * 空值与非空值分支处理
 * @author lyn
 */
public interface PresentOrElseHandler<T extends Object> {

    /**
     * 值不为空时执行消费操作
     * 值为空时执行其他的操作
     * 
     * @param action 值不为空时,执行的消费操作
     * @param emptyAction 值为空时,执行的操作
     * @return void    
     **/
   void presentOrElseHandle(Consumer<? super T> action, Runnable emptyAction);
   
}

2 编写判断方法

创建一个名为isBlankOrNoBlank的方法,方法的返回值为刚才定义的函数式接口-PresentOrElseHandler

  /**
     * 参数为空或不为空时,分别进行不同的操作
     *
     * @param str
     * @return
     **/
    public static PresentOrElseHandler<?> isBlankOrNoBlank(String str) {

        return (consumer, runnable) -> {
            if (str == null || str.length() == 0) {
                runnable.run();
            } else {
                consumer.accept(str);
            }
        };
    }

3 使用方式

调用工具类参数参数后,调用函数式接口presentOrElseHandle方法传入一个ConsumerRunnable

参数不为空时,打印参数

 ConciseUtil.isBlankOrNoBlank("welcome to beijing").presentOrElseHandle(
                System.out::print,
                () -> {
                    System.out.println("空字符串");
                });

存在问题

Consumer<? super T> action

待学习

posted @ 2022-05-07 23:26  进击的小蔡鸟  阅读(1387)  评论(0编辑  收藏  举报