Java可变变量

Java可变变量,java,volatile,Java,Volatile,我试图通过下面的例子来理解volatile的用法。我希望它先打印10,然后再打印15秒。但大多数情况下,我最终得到10分和10分。 是下面代码本身的一些东西 class T implements Runnable { private volatile int x = 10; @Override public void run() { if(x==10) { System.out.println(x); x

我试图通过下面的例子来理解volatile的用法。我希望它先打印10,然后再打印15秒。但大多数情况下,我最终得到10分和10分。 是下面代码本身的一些东西

class T implements Runnable {

    private volatile int x = 10;

    @Override
    public void run() {
        if(x==10) {
            System.out.println(x);
            x = x+ 5;
        } else if(x==15) {
            System.out.println(x);
        }
    }
}


public class Prep {

    public static void main(String [] args) {
        T t1 = new T();
        new Thread(t1).start();
        new Thread(t1).start();
    }
}

您只有一个竞争条件:两个线程并行运行,因此您有(例如)

  • 线程1测试x==10(真)
  • 如果x==10(真),线程2测试
  • 线程1打印10
  • 线程2打印10
x在这里是易变的这一事实与此无关。volatile在本例中保证的唯一一点是如果线程1在线程2读取其值时已经增加了x,那么线程2将看到增加的值。但这并不意味着两个线程不能如上图所示并行运行。

这将起作用:

public static void main(String[] args) {
        T t1 = new T();
        new Thread(t1).start();
        try {
            Thread.currentThread().sleep(1000); // sleeping for sometime .
        } catch (InterruptedException e) {
            // TODO Auto-generated catch block
            e.printStackTrace();
        }
        new Thread(t1).start();
    }

answer : 10 15
原因:行动

if(x==10) {
            System.out.println(x);

可能已首先对第一个线程执行,然后上下文将切换回Thread2(竞争条件如JB Nizet解释的那样),因此当两个线程都打印
x
的值时,它仍然是10。

@user3801948或immutability@user3801948-你真的分享了。。您没有考虑到
if
块中的语句不能保证为一个线程一起执行这一事实。问题在于不共享。该变量是共享的。问题是相互排斥。如果希望单个线程一次执行run()方法,那么应该对其进行同步。