美文网首页
1_基础知识_chapter03_对象的共享_5_安全发布

1_基础知识_chapter03_对象的共享_5_安全发布

作者: 米都都 | 来源:发表于2019-01-21 11:15 被阅读0次
  • (1) Java内存模型为不可变对象的共享提供了特殊的初始化安全性保证, 即使在发布这些对象时没有同步

    (2) 在没有额外同步的情况下, 也可以保证安全访问final类型的域(但是如果final类型的域所指向的是可变对象, 还是需要同步)

  • 一个正确构造的对象, 可以通过以下方式安全发布

    (1) 静态初始化函数中初始化一个对象引用

    JVM内部存在的同步机制保证

    (2) 将对象的引用保存到volatile类型的域或者AtomicReference对象中

    (3) 将对象的引用保存到某个正确构造对象的final类型域中

    (4) 将对象的引用保存到一个由锁保护的域中

    (将对象放入到某个带锁的容器例如Vector, synchronizedList再发布也属于这种情形)

    所有的安全发布机制都能确保, 当对象的引用对所有访问该对象的线程可见时, 对象发布时的状态对于所有线程也将是可见的。如果对象状态不再改变, 那么足以确保任何访问都是安全的

  • 事实不可变对象

    (1) 如果对象从技术上看可变, 但是其状态从发布后不会再改变, 则这种对象称为事实不可变对象(例如java.util.Date类)

    (2) 在没有额外的同步的情况下, 任何线程都可以安全的使用被安全发布的事实不可变对象

  • 可变对象

    不仅在发布时需要使用同步, 每次对象访问时也要使用同步来确保后续修改操作的可见性

    示例

      public class Holder {
    
          private int n;
    
          public Holder(int n) {
    
              this.n = n;
          }
    
          public void assertSanity() {
    
              if (n != n) {
                  throw new AssertionError("This statement is false.");
              }
          }
      }
    

    在多线程环境下, Holder很可能没有被正确发布, 造成某个线程中未必看到其他线程构造好的n的值, 从而造成AssertionError; 如果将n用final修饰, 则可以避免这个问题

  • 对象的发布需求

    不可变对象: 任意机制发布

    事实不可变对象: 安全发布方式(4种)

    可变对象: 由某个锁保护发布

相关文章

网友评论

      本文标题:1_基础知识_chapter03_对象的共享_5_安全发布

      本文链接:https://www.haomeiwen.com/subject/knaqjqtx.html