我正在尝试创建一个示例来显示易失性变量和常用变量之间的区别,例如:
package main;
public class TestVolatile extends Thread {
public int l = 5;
public volatile int m = -1;
public TestVolatile(String str) {
super(str);
}
public void run() {
int i = 0;
while ((l > 1) && (l < 10)) {
if (m >= 0) {
m++;
}
i++;
l = 5;
System.out.println("5=" + i + " m=" + m);
}
}
public static void main(String[] args) throws InterruptedException {
TestVolatile tva = new TestVolatile("ThreadA");
tva.start();
sleep(5);
synchronized (tva) {
tva.m = 5;
tva.l = 10;
}
}
}
So m
是不稳定的,l
不是。我认为退出 while 循环取决于l
.
因为价值l
不是挥发性的 -m
之后将至少增加 1 倍l
被分配了5。但是我已经运行了代码10次并且总是m==5。
所以我想我错了。如何解决这个问题?谢谢。
感谢您的回答,但并非所有都运行良好。
我设置如下:
volatile int x = 0;
volatile int y = 0;
所以现在变量必须相同!但事实并非如此。
x: 346946234 y: 346946250
x: 346946418 y: 346946422
x: 346946579 y: 346946582
x: 346946742 y: 346946745
x: 346946911 y: 346946912
您正在同步主线程和测试线程。因此,Java 保证使其他线程执行的任何更改可见。
顺便说一句,不可能构建一个确定性地显示易失性和非易失性之间差异的示例。您所能希望的最好结果就是获得一个能够以相当高的概率显示差异的程序。如果线程在同一核心上交错运行。你根本无法表现出任何差异。
以下程序在我的计算机上显示了易失性变量和非易失性变量之间的区别。
public class ShowVolatile {
final static int NUM_THREADS = 1;
int x = 0;
volatile int y = 0;
public static void main(String... args) {
final ShowVolatile sv = new ShowVolatile();
for (int i=0; i< NUM_THREADS; i++) {
new Thread(new Runnable() {
public void run() {
while (true) {
sv.x += 1;
sv.y += 1;
}
}
}).start();
}
while (true) {
System.out.println("x: " + sv.x + " y: " + sv.y);
}
}
}
如果增加线程数,您将看到更多的同步丢失。但线程数为 1 就足够了。至少在我的硬件上是四核 i7。
本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)