Multithreading dans Java
Toute application peut avoir plusieurs processus (instances). Chacun de ces processus peut être affecté soit à un seul thread, soit à plusieurs threads. Nous verrons dans ce tutoriel comment effectuer plusieurs tâches en même temps et en apprendrons également plus sur les threads et la synchronisation entre les threads.
Qu’est-ce qu’un fil unique ?
Un seul fil dans Java est fondamentalement une unité de traitement légère et la plus petite. Java utilise des threads en utilisant une « classe de thread ». Il existe deux types de threads : thread utilisateur et thread démon (les threads daemon sont utilisés lorsque nous voulons nettoyer l'application et sont utilisés en arrière-plan). Lorsqu'une application démarre pour la première fois, un thread utilisateur est créé. Après cela, nous pouvons créer de nombreux threads utilisateur et threads démon.
Exemple de thread unique :
package demotest;
public class GuruThread
{
public static void main(String[] args) {
System.out.println("Single Thread");
}
}
Avantages du fil unique :
- Réduit la surcharge de l'application car un seul thread s'exécute dans le système
- Cela réduit également le coût de maintenance de l’application.
Qu’est-ce que le multithreading Java?
multithreading in Java est un processus d'exécution simultanée de deux ou plusieurs threads pour une utilisation maximale du processeur. Les applications multithread exécutent deux ou plusieurs threads exécutés simultanément. Par conséquent, il est également connu sous le nom de Concurrence dans Java. Chaque fil est parallèle les uns aux autres. Plusieurs threads n'attribuent pas de zone mémoire distincte, ils économisent donc de la mémoire. De plus, le changement de contexte entre les threads prend moins de temps.
Exemple de multithread :
package demotest;
public class GuruThread1 implements Runnable
{
public static void main(String[] args) {
Thread guruThread1 = new Thread("Guru1");
Thread guruThread2 = new Thread("Guru2");
guruThread1.start();
guruThread2.start();
System.out.println("Thread names are following:");
System.out.println(guruThread1.getName());
System.out.println(guruThread2.getName());
}
@Override
public void run() {
}
}
Avantages du multithread :
- Les utilisateurs ne sont pas bloqués car les threads sont indépendants et nous pouvons parfois effectuer plusieurs opérations
- En tant que tels, les threads sont indépendants, les autres threads ne seront pas affectés si un thread rencontre une exception.
Cycle de vie des threads en Java
Le cycle de vie d'un thread :

Il existe différentes étapes du cycle de vie du thread, comme le montre le diagramme ci-dessus :
- NOUVEAU
- Exécutable
- Fonctionnement
- Attendre
- Dead
- Nouveau: Dans cette phase, le thread est créé à l'aide de la classe « Thread class ». Il reste dans cet état jusqu'à ce que le programme départs le fil. Il est également connu sous le nom de fil né.
- Exécutable: Dans cette page, l'instance du thread est invoquée avec une méthode start. Le contrôle du thread est donné au planificateur pour terminer l'exécution. Cela dépend du planificateur si le thread doit être exécuté.
- Exécution: Lorsque le thread commence à s’exécuter, l’état passe à l’état « en cours d’exécution ». Le planificateur sélectionne un thread dans le pool de threads et commence à s'exécuter dans l'application.
- Attendre: C'est l'état dans lequel un thread doit attendre. Comme plusieurs threads sont en cours d’exécution dans l’application, une synchronisation entre les threads est nécessaire. Par conséquent, un thread doit attendre que l’autre thread soit exécuté. Par conséquent, cet état est appelé état d’attente.
- Morte: C'est l'état dans lequel le thread est terminé. Le thread est en cours d’exécution et dès qu’il a terminé le traitement, il est dans « l’état mort ».
Méthodes de multithreading dans Java
Certaines des méthodes couramment utilisées pour les threads sont :| Méthode | Description |
|---|---|
| démarrer() | Cette méthode démarre l'exécution du thread et JVM appelle la méthode run() sur le thread. |
| Sommeil (int millisecondes) | Cette méthode met le thread en veille, donc l'exécution du thread s'arrêtera pendant les millisecondes fournies et après cela, le thread recommencera à s'exécuter. Cela aide à la synchronisation des threads. |
| getName () | Il renvoie le nom du fil. |
| setPriority (int nouvelle priorité) | Cela change la priorité du thread. |
| rendement () | Cela provoque l'arrêt du thread actuel et l'exécution d'autres threads. |
Exemple : Dans ce programme multithreading en Java Par exemple, nous allons créer un thread et explorer les méthodes intégrées disponibles pour les threads.
package demotest;
public class thread_example1 implements Runnable {
@Override
public void run() {
}
public static void main(String[] args) {
Thread guruthread1 = new Thread();
guruthread1.start();
try {
guruthread1.sleep(1000);
} catch (InterruptedException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
guruthread1.setPriority(1);
int gurupriority = guruthread1.getPriority();
System.out.println(gurupriority);
System.out.println("Thread Running");
}
}
Explication du code :
- Code Ligne 2: Nous créons une classe « thread_Example1 » qui implémente l'interface Runnable (elle doit être implémentée par toute classe dont les instances sont destinées à être exécutées par le thread.)
- Code Ligne 4: Il remplace la méthode run de l'interface exécutable car il est obligatoire de remplacer cette méthode
- Code Ligne 6: Ici, nous avons défini la méthode principale dans laquelle nous allons démarrer l'exécution du thread.
- Code Ligne 7: Ici, nous créons un nouveau nom de thread sous le nom « guruthread1 » en instanciant une nouvelle classe de thread.
- Code Ligne 8: nous utiliserons la méthode « start » du thread en utilisant l’instance « guruthread1 ». Ici, le thread commencera à s'exécuter.
- Code Ligne 10: Ici, nous utilisons la méthode « sleep » du thread en utilisant l'instance « guruthread1 ». Par conséquent, le thread va dormir pendant 1000 millisecondes.
- Code 9-14: Ici, nous avons placé la méthode sleep dans le bloc try catch car il y a une exception vérifiée qui se produit, c'est-à-dire une exception interrompue.
- Code Ligne 15: Ici, nous définissons la priorité du thread sur 1, quelle que soit la priorité.
- Code Ligne 16: Ici, nous obtenons la priorité du thread en utilisant getPriority()
- Code Ligne 17: Ici, nous imprimons la valeur extraite de getPriority
- Code Ligne 18: Ici, nous écrivons un texte que le fil est en cours d'exécution.
Lorsque vous exécutez le code ci-dessus, vous obtenez le résultat suivant :
Sortie :
5 est la priorité du Thread et Thread Running est le texte qui est la sortie de notre code.
Java Fil à coudre Synchronisation
En multithreading, les programmes ont un comportement asynchrone. Si un thread écrit des données et qu'un autre thread lit des données en même temps, cela peut créer une incohérence dans l'application. Lorsqu'il est nécessaire d'accéder aux ressources partagées par deux ou plusieurs threads, l'approche de synchronisation est utilisée. Java a fourni des méthodes synchronisées pour implémenter un comportement synchronisé.
Dans cette approche, une fois que le thread atteint l'intérieur du bloc synchronisé, aucun autre thread ne peut appeler cette méthode sur le même objet. Tous les threads doivent attendre que ce thread termine le bloc synchronisé et en sorte. De cette façon, la synchronisation est utile dans une application multithread. Un thread doit attendre que l'autre thread termine son exécution, puis les autres threads sont autorisés à s'exécuter.
Il peut s'écrire sous la forme suivante :
Synchronized(object)
{
//Block of statements to be synchronized
}
Multithreading dans Java Exemples de programmes
Dans ce multithreading Java Par exemple, nous prendrons deux threads et récupérerons les noms du thread.
Exemple1:
GuruThread1.java
package demotest;
public class GuruThread1 implements Runnable{
/**
* @param args
*/
public static void main(String[] args) {
Thread guruThread1 = new Thread("Guru1");
Thread guruThread2 = new Thread("Guru2");
guruThread1.start();
guruThread2.start();
System.out.println("Thread names are following:");
System.out.println(guruThread1.getName());
System.out.println(guruThread2.getName());
}
@Override
public void run() {
}
}
Explication du code :
- Code Ligne 3: Nous avons suivi un cours «Guru« Thread1 » qui implémente Runnable (cette interface doit être implémentée par toute classe dont les instances sont destinées à être exécutées par le thread).
- Code Ligne 8: C'est la méthode principale de la classe
- Code Ligne 9: Ici, nous instancions la classe Thread, créons une instance nommée « guruThread1 » et créons un thread.
- Code Ligne 10: Ici, nous instancions la classe Thread, créons une instance nommée « guruThread2 » et créons un thread.
- Code Ligne 11: Nous commençons le fil de discussion, c'est-à-dire guruThread1.
- Code Ligne 12: Nous commençons le fil de discussion, c'est-à-dire guruThread2.
- Code Ligne 13: Afficher le texte sous la forme « Les noms des fils de discussion sont les suivants : »
- Code Ligne 14: Obtenir le nom du thread 1 en utilisant la méthode getName() de la classe thread.
- Code Ligne 15: Obtenir le nom du thread 2 en utilisant la méthode getName() de la classe thread.
Lorsque vous exécutez le code ci-dessus, vous obtenez le résultat suivant :
Sortie :
Les noms de threads sont affichés ici sous la forme
- Guru1
- Guru2
Exemple 2:
Dans ce multithreading dans Java Par exemple, nous allons apprendre à remplacer les méthodes run() et start() d'une interface exécutable, créer deux threads de cette classe et les exécuter en conséquence.
De plus, nous suivons deux cours,
- Celui qui implémentera l'interface exécutable et
- Un autre qui aura la méthode main et s’exécutera en conséquence.
package demotest;
public class GuruThread2 {
public static void main(String[] args) {
// TODO Auto-generated method stub
GuruThread3 threadguru1 = new GuruThread3("guru1");
threadguru1.start();
GuruThread3 threadguru2 = new GuruThread3("guru2");
threadguru2.start();
}
}
class GuruThread3 implements Runnable {
Thread guruthread;
private String guruname;
GuruThread3(String name) {
guruname = name;
}
@Override
public void run() {
System.out.println("Thread running" + guruname);
for (int i = 0; i < 4; i++) {
System.out.println(i);
System.out.println(guruname);
try {
Thread.sleep(1000);
} catch (InterruptedException e) {
System.out.println("Thread has been interrupted");
}
}
}
public void start() {
System.out.println("Thread started");
if (guruthread == null) {
guruthread = new Thread(this, guruname);
guruthread.start();
}
}
}
Explication du code :
- Code Ligne 2: Nous suivons ici un cours «GuruThread2" qui contiendra la méthode principale.
- Code Ligne 4: Ici, nous prenons une méthode principale de la classe.
- Code Ligne 6-7: Nous créons ici une instance de classe GuruThread3 (qui est créé dans les lignes de code ci-dessous) sous le nom « threadguru1 » et nous démarrons le thread.
- Code Ligne 8-9: Nous créons ici une autre instance de classe. GuruThread3 (qui est créé dans les lignes de code ci-dessous) sous le nom « threadguru2 » et nous démarrons le thread.
- Code Ligne 11: Nous créons ici une classe «Guru« Thread3 » implémente l'interface runnable (elle doit être implémentée par toute classe dont les instances sont destinées à être exécutées par le thread).
- Code Ligne 13-14: nous prenons deux variables de classe dont l’une est de type thread class et l’autre de type string.
- Code Ligne 15-18: nous passons outre le GuruLe constructeur Thread3 prend un argument de type chaîne (qui est le nom du thread) qui est affecté à la variable de classe guruname et qui stocke ainsi le nom du thread.
- Code Ligne 20: Ici, nous remplaçons la méthode run() de l'interface exécutable.
- Code Ligne 21: Nous générons le nom du thread à l'aide de l'instruction println.
- Code Ligne 22-31: Ici, nous utilisons une boucle for avec un compteur initialisé à 0, et il ne doit pas être inférieur à 4 (nous pouvons prendre n'importe quel nombre donc ici la boucle s'exécutera 4 fois) et incrémentons le compteur. Nous imprimons le nom du thread et le faisons également dormir pendant 1000 millisecondes dans un bloc try-catch car la méthode sleep a déclenché une exception vérifiée.
- Code Ligne 33: Ici, nous remplaçons la méthode de démarrage de l'interface exécutable.
- Code Ligne 35: Nous affichons le texte « Thread démarré ».
- Code Ligne 36-40: Ici, nous prenons une condition if pour vérifier si la variable de classe guruthread a de la valeur ou non. S'il est nul, nous créons une instance en utilisant une classe de thread qui prend le nom comme paramètre (dont la valeur a été attribuée dans le constructeur). Après quoi le thread est démarré à l’aide de la méthode start().
Lorsque vous exécutez le code ci-dessus, vous obtenez le résultat suivant :
Sortie:
Il y a deux fils de discussion, nous recevons donc deux fois le message « Thread démarré ».
Nous obtenons les noms des threads tels que nous les avons générés.
Il entre dans la boucle for où nous imprimons le compteur et le nom du thread et le compteur commence par 0.
La boucle s'exécute trois fois et entre les deux, le thread est mis en veille pendant 1000 millisecondes.
Par conséquent, d'abord, nous obtenons guru1 puis guru2 puis à nouveau guru2 parce que le thread dort ici pendant 1000 millisecondes, puis ensuite guru1 et encore guru1, le thread dort pendant 1000 millisecondes, donc nous obtenons guru2 puis guru1.
Résumé
Dans ce tutoriel, nous avons vu des applications multithread dans Java et comment utiliser un seul et plusieurs threads dans Java.
- Expliquer le multithreading dans Java:en multithreading, les utilisateurs ne sont pas bloqués car les threads sont indépendants et peuvent effectuer plusieurs opérations à la fois
- Les différentes étapes du cycle de vie du fil sont,
- NOUVEAU
- Exécutable
- Fonctionnement
- Attendre
- Dead
- Nous avons également appris synchronisation entre les threads, ce qui aide l'application à fonctionner correctement.
- Programmation multithread dans Java facilite de nombreuses autres tâches d'application.



