Optional.ofNullable orElse 抛出 NPE

Optional.ofNullable orElse throws NPE

我一直在使用这段代码:

Event rEvent = new Event();

Map<Long, Message> msgMap = getMsg();
Message msg = msgMap.get(rEvent.getMsgId());

Long id = Optional.ofNullable(rEvent.getPkId()).orElse(msg.getPkId());

假设 rEvent.getPkId() 和 msg 都是 null。 所以 Optional.ofNullable(rEvent.getPkId()) 将被跳过,然后 orElse 被执行。在这里它抛出 NPE。 如何使用 Optional.ofNullable 重新编码以进行多次空值检查?

我会简单地使用一个简单的 if else 来处理你的情况:

Long id = null; // default value
if(rEvent.getPkId() != null) {
   id = rEvent.getPkId();
} else if(msg != null){
   id = msg.getPkId();
}

但是如果你想练习Optional,在这种情况下你需要另一个Optional for msg:

Long message = Optional.ofNullable(msg)
        .map(Message::getPkId)
        .orElse(null);// default value OR:
        //.orElseThrow(() -> new IllegalArgumentException("Pk Id shouldn't be null."))

Long id = Optional.ofNullable(rEvent.getPkId()).orElse(message);

Assume rEvent.getPkId() is null and msg also null. So Optional.ofNullable(rEvent.getPkId()) will skipped, then orElse is executed. Here it throws null pointer exception. How to recode this using Optional.ofNullable for multiple null checks?

如果消息为空,您需要事先检查。考虑了以下方法:

public static Long ofNullable(Long ...options){
   return Arrays.stream(options).filter(Objects::nonNull).findFirst().orElseThrow();
}

你的情况:

Long messageID = (msg != null) ? msg.getPkId() : null;
Long id = ofNullable(rEvent.getPkId(), option2, .. option N -1, messageID);

我们首先检查msg是否为null,如果我们仍然在方法ofNullable中使用它,因为它可能发生其他选项不为null,因此可以代替使用。

运行 示例:

public static void main(String[] args) {
    try {
        System.out.println(ofNullable(null, null, null, null));
    }catch (NoSuchElementException e){
        System.out.println("Ups every options is null!");
    }
    System.out.println(ofNullable(null, null, null, 10L));
    System.out.println(ofNullable(null, null, 3L));
    System.out.println(ofNullable(null, 2L, 3L));
    System.out.println(ofNullable(1L, 2L, 3L));
}

输出:

Ups every options is null!
10
3
2
1