Copiez le code comme suit :
// Démarrer le fil de discussion
public void start( );
public void run( );
// Suspend et réveille les threads
public void curriculum vitae( ); // Utilisation non recommandée
public void suspend( ); // Utilisation non recommandée
sommeil vide statique public (longs millis);
sommeil vide statique public (long millis, int nanos);
// Terminer le fil de discussion
public void stop( ); // Utilisation non recommandée
interruption publique nulle ( );
//Obtenir l'état du fil
public booléen isAlive( );
public booléen isInterrupted( );
public statique booléen interrompu( );
// méthode de jointure
public void join( ) lance InterruptedException ;
1. Créez et exécutez des fils de discussion
Le thread n'exécute pas le code dans la méthode run immédiatement après son établissement, mais est dans un état d'attente. Lorsque le thread est en attente, vous pouvez définir divers attributs du thread via les méthodes de la classe Thread, tels que la priorité du thread (setPriority), le nom du thread (setName) et le type de thread (setDaemon).
Lorsque la méthode start est appelée, le thread commence à exécuter le code dans la méthode run. Le thread entre dans l'état d'exécution. Vous pouvez utiliser la méthode isAlive de la classe Thread pour déterminer si le thread est en cours d'exécution. Lorsque le thread est à l'état d'exécution, isAlive renvoie true. Lorsque isAlive renvoie false, le thread peut être à l'état d'attente ou à l'état arrêté. Le code suivant illustre la commutation entre les trois états de création de thread, d'exécution et d'arrêt, et génère la valeur de retour isAlive correspondante.
Copiez le code comme suit :
chapitre 2 du paquet ;
classe publique LifeCycle étend Thread
{
exécution publique vide()
{
entier n = 0 ;
tandis que ((++n) < 1000);
}
public static void main (String[] args) lève une exception
{
Fil LifeCycle1 = new LifeCycle();
System.out.println("isAlive: " + thread1.isAlive());
thread1.start();
System.out.println("isAlive: " + thread1.isAlive());
thread1.join(); // Attendez la fin du thread thread1 avant de continuer l'exécution
System.out.println("thread1 est terminé !");
System.out.println("isAlive: " + thread1.isAlive());
}
}
Veuillez noter que la méthode join est utilisée dans le code ci-dessus. La fonction principale de cette méthode est de garantir que le programme continue de s'exécuter une fois la méthode d'exécution du thread terminée. Cette méthode sera présentée dans un article ultérieur.
Le résultat de l'exécution du code ci-dessus :
est vivant : faux
est vivant : vrai
le fil 1 est terminé !
est vivant : faux
2. Suspendre et réactiver les threads
Une fois que le thread commence à exécuter la méthode run, il ne se terminera pas tant que la méthode run ne sera pas terminée. Cependant, pendant l'exécution du thread, vous pouvez arrêter temporairement l'exécution du thread via deux méthodes. Ces deux méthodes sont la suspension et la mise en veille. Après avoir utilisé suspend pour suspendre un thread, vous pouvez le réactiver via la méthode de reprise. Après avoir utilisé sleep pour mettre le thread en veille, le thread ne peut être dans l'état prêt qu'après le temps défini (une fois la veille du thread terminée, le thread peut ne pas s'exécuter immédiatement, mais entre uniquement dans l'état prêt, en attendant que le système planifie) .
Bien que la suspension et la reprise puissent facilement suspendre et réveiller les threads, l'utilisation de ces deux méthodes peut provoquer des événements imprévisibles. Par conséquent, ces deux méthodes sont marquées comme obsolètes (protestation), ce qui indique que dans le futur jdk. versions, alors essayez de ne pas utiliser ces deux méthodes pour faire fonctionner les threads. Le code suivant montre l'utilisation des méthodes sleep, suspend et restart.
Copiez le code comme suit :
chapitre 2 du paquet ;
la classe publique MyThread étend Thread
{
la classe SleepThread étend Thread
{
exécution publique vide()
{
essayer
{
dormir (2000);
}
attraper (exception e)
{
}
}
}
exécution publique vide()
{
tandis que (vrai)
System.out.println(new java.util.Date().getTime());
}
public static void main (String[] args) lève une exception
{
Fil MyThread = new MyThread();
SleepThread sleepThread = thread.new SleepThread();
sleepThread.start(); // Commence à exécuter le thread sleepThread
sleepThread.join(); // Retarder le thread sleepThread de 2 secondes
thread.start();
indicateur booléen = faux ;
tandis que (vrai)
{
sleep(5000); // Retarde le thread principal de 5 secondes
drapeau = !flag;
si (drapeau)
thread.suspend();
autre
thread.resume();
}
}
}
En apparence, les effets de l'utilisation du sommeil et de la suspension sont similaires, mais la méthode du sommeil n'est pas équivalente à la suspension. La plus grande différence entre eux est que vous pouvez utiliser la méthode suspend dans un thread pour suspendre un autre thread. Par exemple, dans le code ci-dessus, le thread du thread est suspendu dans le thread principal. Sleep ne fonctionne que sur le thread en cours d'exécution. Dans le code ci-dessus, sleepThread et le thread principal dorment respectivement pendant 2 secondes et 5 secondes. Lorsque vous utilisez sleep, sachez que vous ne pouvez pas mettre en veille un thread dans un autre thread. Par exemple, l'utilisation de la méthode thread.sleep(2000) dans la méthode main ne peut pas mettre le thread en veille pendant 2 secondes, mais ne peut mettre le thread principal en veille que pendant 2 secondes.
Il y a deux points à noter lors de l’utilisation de la méthode sleep :
1. La méthode sleep a deux formes surchargées. L'une des formes surchargées peut non seulement définir des millisecondes, mais également des nanosecondes (1 000 000 nanosecondes équivaut à 1 milliseconde). Cependant, la machine virtuelle Java sur la plupart des plates-formes de système d'exploitation n'est pas précise en nanosecondes. Par conséquent, si les nanosecondes sont définies pour la veille, la machine virtuelle Java prendra la milliseconde la plus proche de cette valeur.
2. Throws ou try{...}catch{...} doivent être utilisés lors de l'utilisation de la méthode sleep. Étant donné que la méthode run ne peut pas utiliser de lancers, vous ne pouvez utiliser que try{...}catch{...}. Lorsque le thread est en veille et que la méthode d'interruption (cette méthode sera discutée en 2.3.3) est utilisée pour interrompre le thread, sleep lèvera une InterruptedException. La méthode sleep est définie comme suit :
Copiez le code comme suit :
public static void sleep (long millis) lance InterruptedException
le sommeil vide statique public (long millis, int nanos) lance une exception InterruptedException
3. Trois façons de terminer un fil de discussion
Il existe trois façons de terminer un thread.
1. Utilisez l'indicateur de sortie pour que le thread se termine normalement, c'est-à-dire que le thread se termine lorsque la méthode run est terminée.
2. Utilisez la méthode stop pour forcer l'arrêt du thread (cette méthode n'est pas recommandée car stop, comme la suspension et la reprise, peut également produire des résultats imprévisibles).
3. Utilisez la méthode d'interruption pour interrompre le thread.
1. Terminez le fil de discussion à l'aide de l'indicateur de sortie
Lorsque la méthode run est exécutée, le thread se ferme. Mais parfois, la méthode run ne se termine jamais. Par exemple, utilisez des threads dans des programmes serveur pour surveiller les demandes des clients ou d'autres tâches nécessitant un traitement cyclique. Dans ce cas, ces tâches sont généralement placées dans une boucle, comme une boucle while. Si vous souhaitez que la boucle s'exécute indéfiniment, vous pouvez utiliser while(true){...} pour la gérer. Mais si vous souhaitez que la boucle while se termine dans certaines conditions, le moyen le plus direct consiste à définir un indicateur de type booléen et à définir cet indicateur sur true ou false pour contrôler si la boucle while se termine. Un exemple de terminaison d’un thread à l’aide de l’indicateur de sortie est donné ci-dessous.
Copiez le code comme suit :
chapitre 2 du paquet ;
la classe publique ThreadFlag étend Thread
{
sortie booléenne volatile publique = false ;
exécution publique vide()
{
pendant que (!exit);
}
public static void main (String[] args) lève une exception
{
ThreadFlag thread = new ThreadFlag();
thread.start();
sleep(5000); // Retard du thread principal pendant 5 secondes
thread.exit = true; // Terminer le thread
thread.join();
System.out.println("Thread quitté !");
}
}
Un indicateur de sortie, exit, est défini dans le code ci-dessus. Lorsque exit est vrai, la boucle while se termine et la valeur par défaut de exit est fausse. Lors de la définition de exit, un mot-clé Java volatile est utilisé. Le but de ce mot-clé est de synchroniser exit, ce qui signifie qu'un seul thread peut modifier la valeur de exit en même temps.
2. Utilisez la méthode stop pour terminer le thread
Utilisez la méthode stop pour mettre fin de force à un thread en cours d’exécution ou suspendu. Nous pouvons utiliser le code suivant pour terminer le thread :
thread.stop();
Bien que l'utilisation du code ci-dessus puisse mettre fin au thread, l'utilisation de la méthode stop est très dangereuse, tout comme éteindre soudainement l'ordinateur au lieu de l'arrêter selon la procédure normale, elle peut produire des résultats imprévisibles. Par conséquent, son utilisation n'est pas recommandée. la méthode stop. Terminez le thread.
3. Utilisez la méthode d'interruption pour terminer le thread
L'utilisation de la méthode d'interruption pour terminer un thread peut être divisée en deux situations :
(1) Le thread est dans un état bloqué, par exemple en utilisant la méthode sleep.
(2) Utilisez while(!isInterrupted()){...} pour déterminer si le thread est interrompu.
Dans le premier cas, en utilisant la méthode d'interruption, la méthode sleep lèvera une exception InterruptedException, tandis que dans le second cas, le thread se terminera directement. Le code ci-dessous démontre l'utilisation de la méthode d'interruption dans le premier cas.
Copiez le code comme suit :
chapitre 2 du paquet ;
la classe publique ThreadInterrupt étend Thread
{
exécution publique vide()
{
essayer
{
sleep(50000); // délai de 50 secondes
}
attraper (InterruptedException e)
{
System.out.println(e.getMessage());
}
}
public static void main (String[] args) lève une exception
{
Fil de discussion = new ThreadInterrupt();
thread.start();
System.out.println("Appuyez sur n'importe quelle touche dans les 50 secondes pour interrompre le fil de discussion!");
System.in.read();
thread.interrupt();
thread.join();
System.out.println("Le fil de discussion est terminé !");
}
}
Les résultats de l'exécution du code ci-dessus sont les suivants :
Copiez le code comme suit :
Appuyez sur n'importe quelle touche dans les 50 secondes pour interrompre le fil !
sommeil interrompu
Le fil est terminé !
Après avoir appelé la méthode d'interruption, la méthode sleep lève une exception puis génère le message d'erreur : sleep interrompu.
Remarque : Il existe deux méthodes dans la classe Thread pour déterminer si le thread est terminé via la méthode d'interruption. L'une est la méthode statique interrompue() et l'autre est la méthode non statique isInterrupted(). La différence entre ces deux méthodes est que interrompue est utilisée pour déterminer si le thread actuel est interrompu, tandis que isInterrupted peut être utilisé pour déterminer si. les autres fils de discussion sont interrompus. Par conséquent, while (!isInterrupted()) peut également être remplacé par while (!Thread.interrupted()).