应避免点号链式调用引发的空指针异常,推荐四种方案:①用optional.ofnullable链式map安全解包并orelse兜底;②用objects.requirenonnull在源头校验非空;③拆分步骤显式判空便于调试;④java 14+可用objects.requirenonnullelse简洁设默认值。

直接用点号链式调用(比如 user.getAddress().getCity().toUpperCase())最容易因中间某个环节为 null 而崩溃。这不是语法错误,而是运行时逻辑漏洞——只要任意一环为空,整个表达式就抛出 NullPointerException。避免它的核心思路是:**不让空值穿透到下一层调用**。
用 Optional 链式安全解包
把可能为空的对象包装成 Optional,再用 map 逐层转换,天然阻断空值传播:
-
Optional.ofNullable(user)开始,确保起点不崩 - 每层
.map(User::getAddress)、.map(Address::getCity)都会自动跳过空值,返回空Optional - 最后用
orElse("未知")或ifPresent(System.out::println)统一收口
示例:
Optional.ofNullable(user).map(User::getAddress)
.map(Address::getCity)
.map(String::toUpperCase)
.orElse("N/A");
用 Objects.requireNonNull 做早期拦截
如果某一层的值本就不该为空(比如业务契约要求必须有地址),就在进入长表达式前明确校验:
Objects.requireNonNull(user, "用户不能为空")Objects.requireNonNull(user.getAddress(), "用户地址不能为空")- 之后再放心调用
getCity().toUpperCase()
这种方式让问题在源头暴露,错误信息清晰,比崩溃在第四层更易定位。
在 Java 中初始化和管理阿里云 SDK客户端。包括单例模式、线程安全、endpoint 与 region 配置、VPC 终端节点、同步与异步等。
拆开写 + 明确判空(适合复杂逻辑或调试期)
不追求一行写完,而是分步赋值并检查:
Address address = user != null ? user.getAddress() : null;if (address == null) return "地址缺失";String city = address.getCity();if (city == null) return "城市名为空";return city.toUpperCase();
虽然代码变长,但每一层意图清楚,调试时能准确定位哪一环为空,也方便加日志或默认策略。
用 Java 14+ 的 Objects.requireNonNullElse(简洁兜底)
当某字段为空时想直接给默认值,又不想写 if,可用:
String city = Objects.requireNonNullElse(user.getAddress(), new Address()).getCity();- 注意:仅适用于能构造合理默认对象的场景,避免滥用导致语义失真
比嵌套三元更可读,也比 Optional 少一层包装,适合简单兜底。
Java免费学习笔记:立即使用
解锁 Java 大师之旅:从入门到精通的终极指南










