Multithreading-in Java


Elke applicatie kan meerdere processen (instances) hebben. Elk van deze processen kan worden toegewezen als een enkele thread of meerdere threads. In deze tutorial zullen we zien hoe we meerdere taken tegelijkertijd kunnen uitvoeren en ook meer leren over threads en synchronisatie tussen threads.

Wat is enkele draad?

Eรฉn draadje erin Java is in feite een lichtgewicht en de kleinste verwerkingseenheid. Java gebruikt threads door gebruik te maken van een โ€œThread Classโ€. Er zijn twee soorten threads โ€“ gebruikersthread en daemonthread (daemon threads worden gebruikt wanneer we de applicatie willen opschonen en worden op de achtergrond gebruikt). Wanneer een applicatie voor het eerst start, wordt er een user thread aangemaakt. Daarna kunnen we veel user threads en daemon threads aanmaken.

Voorbeeld met enkele draad:

package demotest;

public class GuruThread
{
       public static void main(String[] args) {
              System.out.println("Single Thread");
       }
}

Voordelen van enkele draad:

  • Vermindert de overhead in de applicatie omdat er een enkele thread in het systeem wordt uitgevoerd
  • Bovendien verlaagt het de onderhoudskosten van de applicatie.

Wat is multithreading? Java?

multithreading in Java is een proces van het uitvoeren van twee of meer threads tegelijk om de CPU maximaal te benutten. Multithreaded applicaties voeren twee of meer threads tegelijk uit. Daarom staat het ook bekend als Concurrency in Java. Elke draad loopt parallel aan elkaar. Meerdere threads wijzen geen afzonderlijk geheugengebied toe en besparen daarom geheugen. Bovendien kost het wisselen van context tussen threads minder tijd.

Voorbeeld van multi-thread:

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() {
    }
}

Voordelen van multithread:

  • De gebruikers worden niet geblokkeerd omdat de threads onafhankelijk zijn en we meerdere bewerkingen tegelijk kunnen uitvoeren
  • Als zodanig zijn de threads onafhankelijk en worden de andere threads niet beรฏnvloed als een thread aan een uitzondering voldoet.

Levenscyclus inpassen Java

De levenscyclus van een thread:

Levenscyclus inpassen Java
Levenscyclus inpassen Java

Er zijn verschillende fasen in de levenscyclus van draad, zoals weergegeven in het bovenstaande diagram:

  1. Nieuwe
  2. uitvoerbare
  3. Hardlopen
  4. Het wachten
  5. Dood
  1. Nieuw: In deze fase wordt de thread gemaakt met behulp van de klasse "Thread class". Deze blijft in deze staat tot het programma starts de draad. Het wordt ook wel geboren draad genoemd.
  2. Uitvoerbaar: Op deze pagina wordt het exemplaar van de thread aangeroepen met een startmethode. De threadcontrole wordt aan de planner gegeven om de uitvoering te voltooien. Het hangt van de planner af of de thread moet worden uitgevoerd.
  3. running: Wanneer de thread wordt uitgevoerd, wordt de status gewijzigd in de status 'actief'. De planner selecteert รฉรฉn thread uit de threadpool en begint met uitvoeren in de applicatie.
  4. Aan het wachten: Dit is de status waarin een thread moet wachten. Omdat er meerdere threads in de applicatie draaien, is er behoefte aan synchronisatie tussen threads. Daarom moet de ene thread wachten totdat de andere thread wordt uitgevoerd. Daarom wordt deze status aangeduid als wachtstatus.
  5. Dood: Dit is de status wanneer de thread wordt beรซindigd. De thread bevindt zich in de actieve status en zodra de verwerking is voltooid, bevindt deze zich in de "dode status".


Methoden voor multithreading in Java

Enkele veelgebruikte methoden voor threads zijn:

Methode Beschrijving
begin() Deze methode start de uitvoering van de thread en JVM roept de run() -methode op de thread aan.
Slaap(int milliseconden) Deze methode zorgt ervoor dat de thread slaapt, waardoor de uitvoering van de thread milliseconden pauzeert en daarna weer start met uitvoeren. Dit helpt bij de synchronisatie van de threads.
getName () Het retourneert de naam van de thread.
setPriority(int nieuweprioriteit) Het verandert de prioriteit van de thread.
opbrengst () Het zorgt ervoor dat de huidige thread wordt stopgezet en dat andere threads worden uitgevoerd.

Voorbeeld: In dit multithreading-programma in Java We gaan bijvoorbeeld een thread maken en de ingebouwde methoden verkennen die beschikbaar zijn voor 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");
  }
}

Uitleg van de code:

  • Code Regel 2: We maken een klasse "thread_Example1" die de Runnable-interface implementeert (deze moet worden geรฏmplementeerd door elke klasse waarvan de instanties bedoeld zijn om door de thread te worden uitgevoerd.)
  • Code Regel 4: Het overschrijft de run-methode van de uitvoerbare interface, omdat het verplicht is om die methode te overschrijven
  • Code Regel 6: Hier hebben we de hoofdmethode gedefinieerd waarmee we de uitvoering van de thread zullen starten.
  • Code Regel 7: Hier creรซren we een nieuwe threadnaam als "guruthread1" door een nieuwe threadklasse te instantiรซren.
  • Code Regel 8: we zullen de โ€œstartโ€ -methode van de thread gebruiken met behulp van de โ€œguruthread1โ€ -instantie. Hier wordt de thread uitgevoerd.
  • Code Regel 10: Hier gebruiken we de โ€œsleepโ€ -methode van de thread met behulp van de instantie โ€œguruthread1โ€. Daarom slaapt de draad gedurende 1000 milliseconden.
  • Code 9-14: Hier hebben we de slaapmethode in het try catch-blok geplaatst, omdat er een gecontroleerde uitzondering is die optreedt, dwz een onderbroken uitzondering.
  • Code Regel 15: Hier stellen we de prioriteit van de thread in op 1, ongeacht de prioriteit die deze had
  • Code Regel 16: Hier krijgen we de prioriteit van de thread met behulp van getPriority()
  • Code Regel 17: Hier drukken we de waarde af die is opgehaald uit getPriority
  • Code Regel 18: Hier schrijven we een tekst die in draad loopt.

Wanneer u de bovenstaande code uitvoert, krijgt u de volgende uitvoer:

Voorbeeld invoegen Java

Output:

5 is de Thread-prioriteit en Thread Running is de tekst die de uitvoer van onze code is.

Java Draad Synckroning

Bij multithreading is er sprake van asynchroon gedrag van de programma's. Als รฉรฉn thread gegevens schrijft en een andere thread tegelijkertijd gegevens leest, kan dit inconsistentie in de applicatie veroorzaken. Wanneer er behoefte is aan toegang tot de gedeelde bronnen door twee of meer threads, wordt de synchronisatiebenadering gebruikt. Java heeft gesynchroniseerde methoden geleverd om gesynchroniseerd gedrag te implementeren.

Bij deze aanpak kan geen enkele andere thread die methode op hetzelfde object aanroepen zodra de thread het gesynchroniseerde blok bereikt. Alle threads moeten wachten tot die thread het gesynchroniseerde blok heeft voltooid en eruit komt. Op deze manier helpt de synchronisatie in een multithreaded applicatie. Eรฉn thread moet wachten tot een andere thread zijn uitvoering heeft voltooid, pas dan mogen de andere threads worden uitgevoerd.

Het kan in de volgende vorm worden geschreven:

Synchronized(object)
{  
        //Block of statements to be synchronized
}

Multithreading-in Java Voorbeeldprogramma's

Bij deze multithreading Java We nemen bijvoorbeeld twee threads en halen de namen van de thread op.

Example1:

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() {
    }
}

Uitleg van de code:

  • Code Regel 3: We hebben een cursus gevolgd.GuruThread1โ€ die Runnable implementeert (deze moet geรฏmplementeerd worden door elke klasse waarvan de instanties bedoeld zijn om door de thread te worden uitgevoerd.)
  • Code Regel 8: Dit is de belangrijkste methode van de klas
  • Code Regel 9: Hier instantiรซren we de Thread-klasse en maken we een instantie met de naam "guruThread1" en maken we een thread.
  • Code Regel 10: Hier instantiรซren we de Thread-klasse en maken we een instantie met de naam "guruThread2" en maken we een thread.
  • Code Regel 11: We starten de draad, dat wil zeggen guruThread1.
  • Code Regel 12: We starten de draad, dat wil zeggen guruThread2.
  • Code Regel 13: De tekst weergeven als "Threadnamen volgen:"
  • Code Regel 14: De naam van thread 1 ophalen met behulp van de methode getName() van de threadklasse.
  • Code Regel 15: De naam van thread 2 ophalen met behulp van de methode getName() van de threadklasse.

Wanneer u de bovenstaande code uitvoert, krijgt u de volgende uitvoer:

Java Multithreading-voorbeeld

Output:

Thread-namen worden hier uitgevoerd als

  • Guru1
  • Guru2

Voorbeeld 2:

Bij deze multithreading in Java We zullen bijvoorbeeld leren over het overschrijven van de methoden run() en start() van een uitvoerbare interface en twee threads van die klasse maken en deze dienovereenkomstig uitvoeren.

We volgen ook twee lessen,

  • Eรฉn die de uitvoerbare interface zal implementeren en
  • Een andere die de hoofdmethode zal hebben en dienovereenkomstig zal worden uitgevoerd.
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();
  }
 }
}

Uitleg van de code:

  • Code Regel 2: Hier volgen we een les.GuruThread2โ€ zal de hoofdmethode bevatten.
  • Code Regel 4: Hier nemen we een hoofdmethode van de klas.
  • Code Lijn 6-7: Hier maken we een instantie van de klasse aan. GuruThread3 (die in de onderstaande regels code wordt aangemaakt) heet "threadguru1" en we starten de thread.
  • Code Lijn 8-9: Hier maken we een nieuwe instantie van de klasse aan. GuruThread3 (die in de onderstaande regels code wordt aangemaakt) heet "threadguru2" en we starten de thread.
  • Code Regel 11: Hier maken we een klasse aan.GuruThread3โ€ implementeert de Runnable-interface (deze moet worden geรฏmplementeerd door elke klasse waarvan de instanties bedoeld zijn om door de thread te worden uitgevoerd).
  • Code Lijn 13-14: we nemen twee klassevariabelen waarvan er รฉรฉn van het type thread-klasse is en de andere van de string-klasse.
  • Code Lijn 15-18: we overschrijven de GuruDe Thread3-constructor accepteert รฉรฉn argument van het type string (de naam van de thread), dat wordt toegewezen aan de klassevariabele guruname, waardoor de naam van de thread wordt opgeslagen.
  • Code Regel 20: Hier overschrijven we de run() -methode van de uitvoerbare interface.
  • Code Regel 21: We voeren de threadnaam uit met behulp van de println-instructie.
  • Code Lijn 22-31: Hier gebruiken we een for-lus met de teller geรฏnitialiseerd op 0, en deze mag niet kleiner zijn dan 4 (we kunnen elk getal nemen, dus de lus wordt hier 4 keer uitgevoerd) en verhogen de teller. We drukken de threadnaam af en laten de thread ook gedurende 1000 milliseconden slapen binnen een try-catch-blok, terwijl de slaapmethode een gecontroleerde uitzondering opleverde.
  • Code Regel 33: Hier overschrijven we de startmethode van de uitvoerbare interface.
  • Code Regel 35: We geven de tekst 'Thread gestart' weer.
  • Code Lijn 36-40: Hier nemen we een if-voorwaarde om te controleren of de klassevariabele guruthread waarde bevat of niet. Als deze nul is, maken we een instantie met behulp van de threadklasse die de naam als parameter aanneemt (waarvoor de waarde is toegewezen in de constructor). Daarna wordt de thread gestart met behulp van de start()-methode.

Wanneer u de bovenstaande code uitvoert, krijgt u de volgende uitvoer:

Multithreading-voorbeeld in Java

uitgang:

Er zijn twee threads, dus we krijgen twee keer het bericht "Thread gestart".

We krijgen de namen van de thread zoals we ze hebben uitgevoerd.

Het gaat naar de for-lus waar we de teller en de draadnaam afdrukken en de teller begint met 0.

De lus wordt drie keer uitgevoerd en tussendoor wordt de draad 1000 milliseconden geslapen.

Daarom krijgen we eerst guru1, dan guru2 en dan weer guru2 omdat de thread hier 1000 milliseconden slaapt en dan de volgende guru1 en opnieuw guru1, de thread slaapt 1000 milliseconden, dus we krijgen guru2 en dan guru1.

Samenvatting

In deze tutorial zagen we multithreaded applicaties in Java en hoe je single- en multi-threads kunt gebruiken Java.

  • Leg multithreading uit Java: bij multithreading worden gebruikers niet geblokkeerd omdat threads onafhankelijk zijn en meerdere bewerkingen tegelijk kunnen uitvoeren
  • Verschillende stadia van de levenscyclus van de draad zijn,
    • Nieuwe
    • uitvoerbare
    • Hardlopen
    • Het wachten
    • Dood
  • Wij hebben er ook over geleerd synchronisatie tussen threads, waardoor de applicatie soepel verloopt.
  • Multithreaded programmeren in Java maakt nog veel meer toepassingstaken eenvoudiger.

Vat dit bericht samen met: