Java 为什么while循环停止工作?

Java 为什么while循环停止工作?,java,javafx,while-loop,Java,Javafx,While Loop,我有两个嵌套的while循环,如果我停止内部循环,外部循环将停止检查内部循环是否运行。我有启动和停止计时器的方法,但是如果我停止计时器,然后重新启动它(将布尔值设置为true),计时器不会启动。如果我在外部循环中执行一些操作,比如System.out.println(“test”),而内部循环暂停,那么它工作正常 @Override protected synchronized Void call() throws Exception { while(true){ Sys

我有两个嵌套的while循环,如果我停止内部循环,外部循环将停止检查内部循环是否运行。我有启动和停止计时器的方法,但是如果我停止计时器,然后重新启动它(将布尔值设置为true),计时器不会启动。如果我在外部循环中执行一些操作,比如System.out.println(“test”),而内部循环暂停,那么它工作正常

@Override
protected synchronized Void call() throws Exception {
    while(true){
        System.out.println();
        while(play){
            System.out.println(play);
            secondCounter++;
            seconds++;
            if(seconds>59){
                secondCounter=0;
                seconds=0;
                minutes++;
            }
            if(minutes>59){
                minutes=0;
                hours++;
            }
            System.out.println("Task sekunden: "+seconds);
            setTime();
            Thread.sleep(1000);
        }
    }
}
以下是完整的课程:

public class TimerTask extends Task<Void>{

private Label timer;
private boolean play=false;

private int secondCounter;

private int seconds;
private int minutes;
private int hours;

public TimerTask(Label timer){
    this.timer=timer;
}

@Override
protected synchronized Void call() throws Exception {
    while(true){
        while(play){
            System.out.println(play);
            secondCounter++;
            seconds++;
            if(seconds>59){
                secondCounter=0;
                seconds=0;
                minutes++;
            }
            if(minutes>59){
                minutes=0;
                hours++;
            }
            System.out.println("Task sekunden: "+seconds);
            setTime();
            Thread.sleep(1000);
        }
    }
}

public int getMinutes(){
    int time;
    time=minutes + (hours*60);
    if(seconds>30){
        time++;
    }
    return time;
}

public void test(){
    String secondsTime;
    String minutesTime;
    String hoursTime;

    if(seconds<10){
        secondsTime="0"+seconds;
    }else{
        secondsTime=String.valueOf(seconds);
    }
    if(minutes<10){
        minutesTime="0"+minutes;
    }else{
       minutesTime=String.valueOf(minutes);
    }
    if(hours<10){
        hoursTime="0"+hours;
    }else{
        hoursTime=String.valueOf(hours);
    }

    System.out.println(hoursTime+":"+minutesTime+":"+secondsTime);
}

public void setTime(){
    String secondsTime;
    String minutesTime;
    String hoursTime;

    if(seconds<10){
        secondsTime="0"+seconds;
    }else{
        secondsTime=String.valueOf(seconds);
    }
    if(minutes<10){
        minutesTime="0"+minutes;
    }else{
       minutesTime=String.valueOf(minutes);
    }
    if(hours<10){
        hoursTime="0"+hours;
    }else{
        hoursTime=String.valueOf(hours);
    }
    Platform.runLater(() -> {timer.setText(hoursTime+":"+minutesTime+":"+secondsTime);});
}

public void stop(){
    this.play=false;
    System.out.println("Stop: "+play);
}

public void start(){
    this.play=true;
    System.out.println("Start: "+play);
}

public void reset(){
    this.play=false;
    secondCounter=0;
    seconds=0;
    minutes=0;
    hours=0;
    timer.setText("00:00:00");
    System.out.println("Reset: "+play);
}
公共类TimerTask扩展任务{
专用标签定时器;
私有布尔播放=假;
私人柜台;
私人整数秒;
私人整数分钟;
私人整数小时;
公共计时器任务(标签计时器){
this.timer=计时器;
}
@凌驾
受保护的同步无效调用()引发异常{
while(true){
边玩{
系统输出打印LN(播放);
secondCounter++;
秒++;
如果(秒>59){
秒计数器=0;
秒=0;
分钟++;
}
如果(分钟>59){
分钟=0;
小时++;
}
System.out.println(“任务sekunden:+秒);
设置时间();
睡眠(1000);
}
}
}
公共int getMinutes(){
整数时间;
时间=分钟+(小时*60);
如果(秒>30){
时间++;
}
返回时间;
}
公开无效测试(){
字符串第二时间;
细线;
字符串小时时间;

如果(秒
播放
是从多个线程读取和修改的,但不是易变的。因此,您无法保证它的可见性。一个线程可以将其设置为true,而另一个线程将其永远视为false

代码的其余部分也不是线程安全的,所有共享状态都是在没有任何同步的情况下访问的


所以你真的不能依赖于代码中的任何东西。

什么是
播放
,你是如何设置的?你的问题很不清楚。显示代码,显示你得到的输出和你期望的输出。什么是
播放
?它是如何定义的?你真的希望在播放时有一个繁忙的循环不断地向输出写入新行吗y是假的?play是一个布尔值,我用一些公共的setter和getter方法设置它,这些方法的代码是关键的。发布它。如果它不是易失性的,那么你的代码就不是线程安全的。我发布了完整的classI只需将布尔值play设置为易失性,它就可以工作了…谢谢。我用synchronized尝试了它,但这让整个GUI挂起了。你可以吗解释一下为什么?这个主题需要一本书来解释。给你买一本“Java并发实践”并阅读它。如果你想认真对待Java中的多线程,这是一本必读的书。