Qu'est-ce que je n'ai pas compris dans les threads ?
Bonjour,
J'ai lu plusieurs articles sur les Threads. J'avais cru comprendre que lorsqu'un thread quitte sa méthode run il prend l'état TERMINATED.
Aussi est-ce que quelqu'un peut m'expliquer ce qui ne marche pas dans le code suivant ?
La classe interface graphique avec une méthode main(). On lance le thread avec le bouton play, on l'arrête avec le bouton stop (rien de bien original donc)
Code:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74
|
public class Essai extends JFrame implements ActionListener, ObservateurFil
{
private Fil monThread;
private JButton stop = new JButton("Stop") ;
private JButton play = new JButton("Play");
private boolean boucle = false;
public Essai ()
{
super("test Thread");
setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
monThread = new Fil();
monThread.ajouteObservateur(this);
JPanel boutons = new JPanel();
boutons.setLayout(new FlowLayout());
play.setEnabled(true);
stop.setEnabled(false);
play.addActionListener(this);
stop.addActionListener(this);
boutons.add(stop);
boutons.add(play);
this.add(boutons,BorderLayout.SOUTH);
pack();
setLocationRelativeTo(null);
setVisible(true);
}
@Override
public void actionPerformed(ActionEvent e)
{
if (e.getSource() == stop) stop();
else if (e.getSource() == play) play();
}
private void play()
{
System.out.println("j'ai cliqué sur play : " + monThread.getState());
if (monThread.getState() == State.TERMINATED)
{
monThread = new Fil();
}
stop.setEnabled(true);
play.setEnabled(false);
monThread.setEtat(EtatFil.PLAY);
if (monThread.getState() == State.NEW) monThread.start();
}
private void stop()
{
stop.setEnabled(false);
play.setEnabled(true);
monThread.setEtat(EtatFil.STOP);
System.out.println("fin du Thread " + monThread.getState());
}
@Override
public void finThread()
{
stop();
if (boucle) play();
}
public static void main(String ...args)
{
javax.swing.SwingUtilities.invokeLater(new Runnable()
{
public void run()
{
new Essai();
}
});
}
} |
La classe qui représente un Thread. Au lancement du thread, on stocke l'heure de début du thread, puis on lance une boucle sans fin qui s'arrête soit par l'appui sur STOP soit parce que le temps est écoulé.
Code:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51
|
public class Fil extends Thread
{
private EtatFil etat;
private ObservateurFil observateur;
private List<ObservateurFil> observateurs = new ArrayList<ObservateurFil>();
public Fil()
{
super("Test Thread");
etat = EtatFil.STOP;
}
public void ajouteObservateur(ObservateurFil of)
{
this.observateur = of;
}
public void run()
{
long debut = System.currentTimeMillis();
int m = -1;
while(true)
{
if (etat == EtatFil.STOP || etat == EtatFil.EOM)
{
break;
}
if(etat == EtatFil.PLAY)
{
int t = (int) ((System.currentTimeMillis() - debut)/1000);
if (t != m)
{
m = t;
System.out.println(m);
}
//on arrive à la fin du comptage, on arrête
if (m > 4)
{
etat = EtatFil.EOM;
}
}
}
observateur.finThread();
}
public void setEtat(EtatFil e)
{
etat = e;
}
} |
Une énumération des divers états du fil
Code:
1 2 3 4 5
|
public enum EtatFil
{
STOP, PAUSE , PLAY, EOM;
} |
L'interface pour les observateurs
Code:
1 2 3 4 5
|
public interface ObservateurFil
{
public void finThread();
} |
Quand je clique sur PLAY puis sur STOP j'ai cela dans la console.
j'ai cliqué sur play : NEW
0
1
2
fin du Thread RUNNABLE
fin du Thread RUNNABLE
J'ai deux questions :
pourquoi ai-je deux fois la ligne "fin du Thread RUNNABLE" ?
pourquoi l'état n'est pas TERMINATED ?