Qu'est-ce que Monitor en Java

Mohammad Irfan 12 octobre 2023
  1. Exemple de multithreading sans utiliser Monitor en Java
  2. Exemple de multithreading utilisant Monitor en Java
Qu'est-ce que Monitor en Java

Ce tutoriel présente ce qu’est un moniteur et comment l’utiliser dans la programmation Java.

Monitor est un terme qui fait référence à la synchronisation des processus. Ceci est initialement utilisé par les systèmes d’exploitation, et maintenant la plupart des langages de programmation l’utilisent.

En Java, il est utilisé pour réaliser la synchronisation des processus dans un environnement multithread. Elle permet de parvenir à une exclusion mutuelle entre les processus. Le processus externe ne peut pas accéder au code écrit dans le moniteur, donc aucune situation d’attente et de maintien ne se produit.

Java utilise la méthode synchronized() pour créer un moniteur, et n’importe quel objet peut servir de moniteur. Un moniteur utilise une fonction associée à une donnée/variable spécifique comme verrou. Lorsqu’un thread essaie d’accéder à ces données et de les modifier, le moniteur restreint ce processus et le maintient jusqu’à ce que le thread actuel termine son exécution.

Comprenons le moniteur avec quelques exemples.

Exemple de multithreading sans utiliser Monitor en Java

Comprenons d’abord ce qui se passe si nous n’utilisons pas le moniteur en programmation multithread. Dans cet exemple, nous avons créé deux threads et les avons exécutés. Nous pouvons remarquer que l’exécution des threads est complètement aléatoire, et à chaque fois que thread1 ou thread2 démarre l’exécution. Dans le cas du moniteur, un seul thread peut exécuter son code à la fois, et le deuxième thread doit attendre ce temps, mais ici nous n’avons pas utilisé de moniteur, donc le résultat est complètement brouillon. Voir l’exemple ci-dessous.

class MonitorDemo {
  void showMsg(String msg) { // synchronized method
    for (int i = 1; i <= 5; i++) {
      System.out.println(msg);
      try {
        Thread.sleep(500);
      } catch (Exception e) {
        System.out.println(e);
      }
    }
  }
}
class Thread1 extends Thread {
  MonitorDemo m;
  Thread1(MonitorDemo m) {
    this.m = m;
  }
  public void run() {
    m.showMsg("thread1");
  }
}
class Thread2 extends Thread {
  MonitorDemo m;
  Thread2(MonitorDemo m) {
    this.m = m;
  }
  public void run() {
    m.showMsg("thread2");
  }
}
public class SimpleTesting {
  public static void main(String args[]) {
    MonitorDemo obj = new MonitorDemo();
    Thread1 t1 = new Thread1(obj);
    Thread2 t2 = new Thread2(obj);
    t1.start();
    t2.start();
  }
}

Production :

thread1
thread2
thread1
thread2
thread1
thread2
thread1
thread2
thread1
thread2

Exemple de multithreading utilisant Monitor en Java

Ici, nous avons créé un moniteur dans cet exemple, et nous avons marqué la méthode showMsg() comme synchronisée. Ainsi, un seul thread peut y accéder à la fois. Vous remarquerez la sortie cette fois ; le deuxième thread ne démarre l’exécution qu’après avoir terminé le premier thread qui synchronise le code, et c’est l’avantage du moniteur. Il est utile dans la programmation multithread lorsque plusieurs threads demandent la même ressource. Nous devons créer un tel système pour éviter tout problème d’impasse ou de famine. Voir l’exemple ci-dessous.

class MonitorDemo {
  synchronized void showMsg(String msg) { // synchronized method
    for (int i = 1; i <= 5; i++) {
      System.out.println(msg);
      try {
        Thread.sleep(500);
      } catch (Exception e) {
        System.out.println(e);
      }
    }
  }
}
class Thread1 extends Thread {
  MonitorDemo m;
  Thread1(MonitorDemo m) {
    this.m = m;
  }
  public void run() {
    m.showMsg("thread1");
  }
}
class Thread2 extends Thread {
  MonitorDemo m;
  Thread2(MonitorDemo m) {
    this.m = m;
  }
  public void run() {
    m.showMsg("thread2");
  }
}
public class SimpleTesting {
  public static void main(String args[]) {
    MonitorDemo obj = new MonitorDemo();
    Thread1 t1 = new Thread1(obj);
    Thread2 t2 = new Thread2(obj);
    t1.start();
    t2.start();
  }
}

Production :

thread1
thread1
thread1
thread1
thread1
thread2
thread2
thread2
thread2
thread2