Java中的原子性和内存顺序

我是Java的新手,目前正在阅读《 Java:初学者指南》第六版.我在Java的原子性和内存顺序方面遇到了一些困惑.

在本书涉及多线程的示例中,对共享资源(例如,共享变量)的并发访问不会同步,共享资源也不会被明确标记(例如,原子或易失性或类似的东西).例如,在“尝试此15-1”(第519页)中,对共享变量stopFlag的并发访问未序列化,也未明确标记该变量.

根据this,即使没有特别标记,也保证Java中的某些数据类型是原子的.这在某种程度上解决了关于原子性的考虑.但是记忆顺序如何?默认处理是否暗含顺序一致性,就像对C中的原子类型进行访问时的默认memory_order_seq_cst处理一样?

以下是该示例中的一些关键代码段.

public class Banner extends Applet implements Runnable {
  String msg = " Java Rules the Web ";
  Thread t;
  boolean stopFlag;
  // Initialize t to null.
  public void init() {
    t = null;
  }

  // Start thread
  public void start() {
    t = new Thread(this);
    stopFlag = false;
    t.start();
  }

  // Entry point for the thread that runs the banner.
  public void run() {
    // Redisplay banner
    for( ; ; ) {
      try {
        repaint();
        Thread.sleep(250);
        if(stopFlag) break;
      } catch(InterruptedException exc) {}
    }
  }

  // Pause the banner.
  public void stop() {
    stopFlag = true;
    t = null;
  }

  // Display the banner.
  public void paint(Graphics g) {
    char ch;
    ch = msg.charAt(0);
    msg = msg.substring(1, msg.length());
    msg += ch;
    g.drawString(msg, 50, 30);
  }

解决方法:

没有.

如果使用诸如AtomicInteger之类的数据结构,则是的,set()操作隐含强存储顺序,就像该类中的其他一些操作一样.此处使用的“原子”一词表示该类实现了一组原子操作(例如compareAndSet),这些原子操作通常由子操作组成.顺便提及,这些类型的数据结构通常遵循强存储顺序,并且通过词关联,在这种上下文中使用的“原子”通常表示强存储顺序. (但并非总是如此,例如AtomicInteger中的lazySet和weakCompareAndSet)

回到您的问题,“原子”一词没有这样的含义,仅表示写作不可分割.但这是没有意义的.有意义的是说,对非易失性long或double变量的写操作是“非原子的”,因为它等效于两次写操作(JLS#17.7).其他写操作也不是非原子的.

上一篇:Android SyncAdapter中的重试机制


下一篇:java-在不同的类(和不同的包)中同步两个方法