为什么Java8中的Optional类是final的

2018-08-03  本文已影响0人  断臂残猿

Java8的Optional类给我们发日常开发中规避null判断提供了极大便利,现在我的代码中已经几乎很少使用if (sth == null)的写法,基本都用Optional.ofNullable(sth)了。

但是如果使用过程中感觉Optional的API不够用怎么办?
比如我想实现这样的效果:

                if (sth == null) {
                    throw new Exception();
                } else {
                    doSth();
                }

Optinal提供了ifPresent来执行非空时的操作,但是没有提供类似ifNotPresent的操作符。那该怎么办呢?总不能这样写吧:

                    if (opt.isPresent()) {
                        doSth(opt.get());
                    } else {
                        throw new Exception();
                    }

太不伦不类了,不是纯粹的函数式编程。

Java9给Optional类添加了一个方法

public void ifPresentOrElse(Consumer<? super T> action, Runnable emptyAction) {
    if (value != null) {
        action.accept(value);
    } else {
        emptyAction.run();
    }
}
比如jdk自带的模块分析器中有这样的代码:

找到模块就add,否则log。

所以自然而然的想到模仿这个方法,自定义一下Optional类。
可是回头一看:Optional类是申明为final的!!没法继承啊!

为什么呢?
因为像Optional类和LocalDateTime类都是值敏感的。jdk要求把值敏感的类设计成不可变类,否则对象就可以被变更。

值敏感类一般有这么几个特征要求:

如果值敏感却可以继承,我们就可以写出这样的代码:

public static void main(String[] args) {
    System.out.println(OptionalNotFinal.of(3).b);
    System.out.println(MyOptional.of(3).set(5).b);
}

private static class OptionalNotFinal {
    private final int b;

    private OptionalNotFinal(){
        b = 0;
    }

    private OptionalNotFinal(int b) {
        this.b = b;
    }

    public static OptionalNotFinal of(int b) {
        return new OptionalNotFinal(b);
    }
}

private static class MyOptional extends OptionalNotFinal {
    private int b;

    private MyOptional(){
        b = 0;
    }

    private MyOptional(int b) {
        this.b = b;
    }

    public static MyOptional of(int b) {
        return new MyOptional(b);
    }

    public MyOptional set(int b) {
        this.b = b;
        return this;
    }
}

显然已经偏离了该类的初衷。

上一篇下一篇

猜你喜欢

热点阅读