这实际上是不正确的,因为null 属性在语义上与带有一些默认值的该属性不同。因此,为缺失值设置一些 new Account() 到 account 属性是不正确的。
如果您想简化代码,请考虑使用JAXB2 Fluent API plugin。您可能会得到如下代码:
rootObject.withAccount().getAccountName()
(隐式初始化 account。)我不能 100% 确定它是否会以这种方式工作,但绝对值得一试。
更新
关于你的 cmets 的一些注意事项。
我查看了您发布的链接并尝试在线查找它,但如果我理解正确,它主要用于填充对象中的值而不是读取它们。您发送的链接说:FluentApi 插件为 bean setter 提供了方法链。我正在寻找一种方法来避免在尝试访问嵌套类时检查空值。
你是对的。但是,您具体说“解组完整的对象树以包括那些代表缺失元素的对象”。我的观点是,JAXB 填写这些缺失的属性是不正确的,但是 you 可以做到这一点,并且 Fluent API 插件是我知道的一个易于使用的 API 的终结点案子。但这并不能回答您的问题,因为目前可能没有答案。
那里的 cmets 大多建议要么吸收它并一路检查空值,使用反射,或者只是捕获错误。出于性能考虑,我最终选择了第一个选项。
可能是你目前能做的最好的事情。这就是我一直在做的事情(检查nulls)。嗯,不是很好,但也很琐碎。
接下来,我想谈谈如何解决这个问题?
XJC 支持plugins,可以扩充生成的代码。这是一个非常强大的工具,我用这些插件做了很多。但是应该生成什么代码呢?它在 Java 中应该是什么样子的?
用默认值填充属性是不正确的。我认为这种方式不会带来好的结果。
rootObject.getAccount().getAccountName() 之类的东西由于nulls 而无法工作。那么它在 Java 中会是什么样子呢?
我想到的最好的事情是getValueByPath(String propertyPath) 这样的界面,这样您就可以执行以下操作:
rootObject.getValueByPath(`account.accountName`);
getValueByPath(String path) 可以由插件生成。可以生成无需任何反射即可解析此类paths 的代码。生成的代码将检查自己的属性并返回目标值,或在其上调用getValueByPath(...),如果未找到则返回null/null。
但是你不会有自动完成功能,整个事情会更容易出错。