簡體   English   中英

Thread.sleep如何真正起作用?

[英]How does Thread.sleep really work?

我編寫了一個程序,該程序會不時設置按鈕的setEnable Thread.sleep()在另一個類中。 這是代碼:

import javax.swing.*;
import java.awt.*;
import java.awt.event.*;

public class Try extends JFrame implements ActionListener{
JButton n1 = new JButton("1");
JButton n2 = new JButton("2");
JButton n3 = new JButton("3");
JButton show = new JButton("Show");

{
show.addActionListener(this);
n1.setEnabled(false);
n2.setEnabled(false);
n3.setEnabled(false);

}

public Try(){
  super("Try");
  setVisible(true);
  setSize(500, 200);
  setLayout(new GridLayout(1, 4));
  add(n1);
  add(n2);
  add(n3);
  add(show);
}  

public void actionPerformed(ActionEvent a) {
Object clicked = a.getSource();
if(show == clicked){
new EasyLevel1().start();
}
}

  class EasyLevel1 extends Thread {
    public void run() {      
        try {
            n1.setEnabled(true);
            Thread.sleep(1000);
            n1.setEnabled(false);
            n2.setEnabled(true);
            Thread.sleep(1000);
            n2.setEnabled(false);
            n3.setEnabled(true);
            Thread.sleep(1000);
            n3.setEnabled(false);    
        } catch (InterruptedException e){
        }
        }
      }

    public static void main(String[] args){
      Try frame = new Try();
      frame.setVisible(true);
    }
    }

但是,當我將其放在類中的actionListener

import javax.swing.*;
import java.awt.*;
import java.awt.event.*;

public class Try extends JFrame implements ActionListener{
JButton n1 = new JButton("1");
JButton n2 = new JButton("2");
JButton n3 = new JButton("3");
JButton show = new JButton("Show");

{
show.addActionListener(this);
n1.setEnabled(false);
n2.setEnabled(false);
n3.setEnabled(false);

}

public Try(){
  super("Try");
  setVisible(true);
  setSize(500, 200);
  setLayout(new GridLayout(1, 4));
  add(n1);
  add(n2);
  add(n3);
  add(show);
}  

public void actionPerformed(ActionEvent a) {
Object clicked = a.getSource();
if(show == clicked){
            try {n1.setEnabled(true);
            Thread.sleep(1000);
            n1.setEnabled(false);
            n2.setEnabled(true);
            Thread.sleep(1000);
            n2.setEnabled(false);
            n3.setEnabled(true);
            Thread.sleep(1000);
            n3.setEnabled(false);
            } catch (InterruptedException e){}
}
}

public static void main(String[] args){
  Try frame = new Try();
  frame.setVisible(true);
}
}

它凍結了我的整個程序,根據該示例,我了解到應該在另一個線程中運行線程睡眠以阻止當前類凍結。 但是我希望新的thread.sleep仍然凍結其操作,就像它將仍然執行上面的代碼一樣,但是按鈕將響應,因為它在另一個線程中。 但是令人驚訝的是,它完成了我想要的工作,沒有像第一個程序那樣立即將所有內容設置為禁用。

Thread.sleep()使當前線程暫停。 您正在actionPerformed中運行它,即在Swing事件中運行它。 所有Swing操作都在單個線程EDT中完成。 當您使用Thread.sleep()暫停它時,Swing無法處理任何其他事件,因為您尚未從actionPerformed偵聽器返回。 因此,GUI凍結(不是完整的應用程序,只是GUI)。

通常,因此,在Swing事件中執行長時間運行的操作是一種不好的做法。 對於您想做的事情,一個不錯的選擇是使用Swing計時器。

Thread.sleep將使執行調用的線程在指定時間(或直到線程被中斷)進入睡眠狀態。 當您在actionPerformed方法中調用它時,它將導致UI線程進入休眠狀態。 這就是您的程序被鎖定的原因。

您應該啟動一個單獨的線程,該線程將在您之間處於休眠狀態時逐步處理您想進行的各種調用。 另外(我認為更好的是),您可以使用Swing計時器執行所需的操作。

發生的是,在第二個示例中, Thread.sleep阻止了EDT因此沒有進一步的UI更新發生。 相反,在第一個示例中,您在分離Thread中調用sleep ,因此不會發生“凍結”。 對於此類任務,首選使用Swing計時器

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM