请稍等 ...
×

采纳答案成功!

向帮助你的同学说点啥吧!感谢那些助人为乐的人

老师救命啊,我的程序使用volatile依然存在可见性问题

public class FieldVisibility {

  volatile int a = 1;
  volatile int b = 2;

//  static final Set<ExecutionResult> results = new HashSet<>();

  /**
   * 四种结果:
   * ExecutionResult{a=3, b=2} write1 -> read -> write2
   * ExecutionResult{a=3, b=3} write1 -> write2 -> read
   * ExecutionResult{a=1, b=2} read -> write1 -> write2
   * ExecutionResult{a=1, b=3} 发生可见性问题
   *
   * 解决可见性问题可以使用volatile关键字,修饰之后运行结果:
   *
   * @param args
   * @throws InterruptedException
   */
  public static void main(String[] args) throws InterruptedException {

    for(int i=0;i<50000;i++) {
      FieldVisibility fieldVisibility = new FieldVisibility();

      Thread thread1 = new Thread(() -> {
        try {
          Thread.sleep(1);
        } catch (InterruptedException e) {
          e.printStackTrace();
        }
        fieldVisibility.change();
      });

      Thread thread2 = new Thread(() -> {
        try {
          Thread.sleep(1);
        } catch (InterruptedException e) {
          e.printStackTrace();
        }
        fieldVisibility.print();
      });

      thread1.start();
      thread2.start();
//      thread1.join();
//      thread2.join();
    }
//    for(ExecutionResult result : results) {
//      System.out.println(result.toString());
//    }
  }

  public void change() {
    a = 3;
    b = a;
  }

  public void print() {
//    results.add(new ExecutionResult(a, b));
    System.out.println("a=" + a + "; b=" + b);
  }
}

救命,老师,同学们!

正在回答 回答被采纳积分+3

2回答

悟空 2020-01-01 23:48:09

这个问题我找到了,你看一下:http://coding.imooc.com/learn/questiondetail/141325.html

0 回复 有任何疑惑可以回复我~
悟空 2020-01-01 15:31:24

改变打印时候a和b的顺序
打印不是原子的
这个问题有同学提过一样的,你看一下问答区哈

0 回复 有任何疑惑可以回复我~
  • 提问者 长袜子皮皮93 #1
    亲爱的老师,但是print本身也是对a和b的一种读操作呀,既然加了volatile关键字为就应该只有三种情况呀
    回复 有任何疑惑可以回复我~ 2020-01-01 15:32:55
  • 提问者 长袜子皮皮93 #2
    当我没说,我在想一想奥
    回复 有任何疑惑可以回复我~ 2020-01-01 15:33:27
  • 提问者 长袜子皮皮93 #3
    明白了,加了volatile关键字排除可见性问题,就剩下线程切换带来的结果,两个线程各自的读写操作4!个可能,排除writeb-writea的情况。再锁定先读b再读a,就永远不会得到b被修改了a却不变;我的天,那线程切换再加上可见性问题那就太太复杂了,啊啊啊
    回复 有任何疑惑可以回复我~ 2020-01-01 15:58:45
问题已解决,确定采纳
还有疑问,暂不采纳
意见反馈 帮助中心 APP下载
官方微信