I am facing a problem which two threads are accessing shared variables without the ability to the see last changes.
I have a GUI thread that has a text box, a mouse click listener that once recorded a click, creates a new thread which injects values to the text box and when a second mouse click is invoked the last created thread will be stopped and a new one will be created that will inject values as well and so on..
public class SomeGuiClass{
private static boolean isRunning = false;
private static boolean canRun = true;
private Thread thread;
public SomeGuiClass(){
txt.addMouseListener(new MouseListener() {
@Override
public void mouseDoubleClick(MouseEvent arg0) {
if (isRunning){
// force the thread to stop running.
canRun = false;
// waits for the thread to stop his run.
while(isRunning);
}
thread = new Thread(new Runnable() {
@Override
public void run() {
SomeGuiClass.isRunning = true;
while(SomeGuiClass.canRun){
// Inject values to text box, using Display.asyncExec...
Thread.sleep(1000);
}
SomeGuiClass.isRunning = false;
}
});
SomeGuiClass.canRun = true;
thread.start();
}
}
}
}
I tried using volatile and the same thing happens. It seems that what I am doing is logically right, only a lack of technical information about how the java memory model is missing.
Several observations :
You have to make both isRunning
and canRun
volatile to make it work
Since your other thread is only checking canRun
every 1000 ms, you might still have long delay before processing your second call to mouseDoubleClick
on GUI thread.
It is generally a very bad idea to make threads do busy-waiting with
while(true){/*do nothing*/}
loop. You should definitely use wait/notify mechanism instead to sync between threads
The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.