我猜JAXB调用零参数构造函数,然后开始填充非易失性字段并将内容添加到列表中。
在我自己的代码中在执行此操作(解组)之后,生成的bean会立即通过某些add方法逐出一些工作线程,但不能通过构造函数或任何其他方式触发内存模型,用于刷新和从共享区域重新获取数据。
这样安全吗?或者JAXB在幕后做了一些魔术?我想不出java编程语言中的任何方式都可以强制所有线程都可见。 JAXB生成的bean的用户是否必须担心在并发设置中可能没有明显设置字段?
编辑:为什么会有这么多的downvotes?没有人能够解释JAXB如何确保这个看似不可能完成的任务。
答案 0 :(得分:3)
我不会费心去调查你问题中的各种“事实”,我只想解释一下:
“没有引用就不行了!”
也就是说,如今处理Java中的线程的任何人都必须尝试以避免在之前发生发生 - 之后发生无意中的关系。任何使用volatile变量,synchronized块,Lock对象或原子变量都必然会建立这种关系。这会立即引入阻塞队列,同步哈希映射以及其他许多碎片。
你如何确定JAXB实现真的设法做错了什么?
尽管如此,虽然从JAXB获得的对象与JAXB完成后的任何Java对象一样安全,但编组/解组方法本身are not thread-safe。我相信你不必担心,除非:
您的线程共享JAXB处理程序对象。
你在没有同步的线程之间传递对象:一种明显不健康的做法,无论这些对象来自哪里......
修改强>
既然您已经编辑了问题,我们可以提供更具体的答案:
JAXB生成的对象与任何其他Java对象一样是线程安全的,完全没有。直接构造函数调用本身也不提供线程安全性。如果没有建立的发生在之前的关系,JVM可以在调用new
时自由返回部分初始化的对象。
有 方式,即通过use of final fields and immutable objects,以避免这个陷阱,但很难做到正确,especially with JAXB,它实际上并没有解决传播正确的对象引用的问题,以便所有线程都在查看同一个对象。
底线:您可以通过使用正确的同步方法安全地在线程之间移动数据。除了明确记录的内容之外,不要假设任何有关底层实现的内容。即便如此,最好还是安全地进行防御和编码 - 这通常会导致线程之间更清晰的交互。如果在稍后阶段,分析器指示性能问题,然后您应该开始考虑微调同步代码。