Java-szálak
Ez a szócikk nem tünteti fel a független forrásokat, amelyeket felhasználtak a készítése során. Emiatt nem tudjuk közvetlenül ellenőrizni, hogy a szócikkben szereplő állítások helytállóak-e. Segíts megbízható forrásokat találni az állításokhoz! Lásd még: A Wikipédia nem az első közlés helye. |
A Java nyelvi környezet alkalmas többszálú programok készítésére, futtatására.
Szálak használata
A Java programozási nyelvben a szálakat tipikusan a következő célokra használják:
- a program gyorsítására, oly módon, hogy a nagyobb teendők egy-egy szálba rendezhetők, így a megfelelő ütemezés mellett a program futási ideje rövidülhet;
- a program egy száljának rövid idejű felfüggesztésére.
A szál felfüggesztése a Thread
osztály sleep
metódusa meghívásával oldható meg, aminek argumentumként szál/program felfüggesztésének idejét kell megadni (ezredmásodpercben). Mindez a szálak összehangolására is használható.
Pl: Thread.sleep(1000);
Itt az adott szál futása 1 másodpercig lesz felfüggesztve.
Szálak létrehozása
Egy szál létrehozásának két lehetséges módja van:
- Örököltethető a
Thread
osztályból az új osztály, melynek arun
metódust kell felüldefiniálni, - Létrehozható a
Runnable
interfész implementálásával, amit át kell adni aThread
konstruktorának, ezután már el lehet indítani szálat astart
metódussal.
Példa ez utóbbira:
public class TestThread implements Runnable {
public void run () {
System.out.println("Helló világ");
}
public static void main (String[] args) {
Thread thread = new Thread(new TestThread());
thread.start();
}
}
Szinkronizáció
Egy többszálú Java program egyszerre számos feladatot tud végrehajtani, függetlenül a processzormagok számától. A programok futtatásáért felelős JVM (Java virtuális gép, az angol Java Virtual Machine rövidítése) a saját ütemezője szerint választja ki, hogy éppen melyik szálat futtatja. Mindez JVM-implementáció függő, és befolyásolható több módon is:
- A
Thread.sleep();
utasítással várakoztathatók (időzíthetők) a különböző szálak. Például: két vagy több szálat használó program esetén, hogy a szálakat ne zavarják egymást. Az egyiket (vagy a többit) elaltatjuk annyi időre, hogy akkor "ébredjen(ek) fel", mikor a másik befejezte munkáját. - Vannak olyan helyzetek, mikor azt szeretnénk, hogy egy objektumot a konzisztencia érdekében egyszerre csak egy szál használhasson. Ez a
synchronized
kulcsszó használatával valósítható meg. Az objektum szinkronizálható egy metódushívás vagy egy utasításblokk idejére.
Az alábbi példában a saját objektum blokkolódik más szálak számára a Hello metódus végrehajtása alatt:
public synchronized void Hello() {
System.out.println("Helló, világ!");
}
A blokkszintű szinkronizáció esetében tetszőleges blokkolandó objektum is megadható. A saját objektum blokkolásához nem kell megadni nevesített objektumot, ill. explicit módon a this kulcsszó is használható erre a célra.
A szinkronizáció a memóriaszervezést is érinti. A JVM minden szál számára saját memória-gyorsítótárat tart fenn. A szinkronizált programrészek végrehajtása alatt minden adatmódosítás kizárólag a gyorsítótárat érinti, kivéve ha az adott objektum volatilis, azaz nem gyorstárazható. Így az olvasási blokkolás nem is szükséges, tehát végeredményben csak az adott metódus kerül teljes blokkolásra.
Új lehetőségek
A java 1.5-től új szinkronizációs lehetőségeket kínál, nem nyelvi szinten, hanem új osztálykönyvtár biztosításával:
Task Scheduling Framework: az Executor-ok segítségével jobban szervezhetők például az opcionálisan időzített szálak
Concurrent Collections: a szokásos gyűjteménytípusok szálbiztos változatait tartalmazza
Atomic Variables: lehetőség összetett atomi műveleteket támogató változók használatára (pl. növelés és lekérdezés; összehasonlítás és beállítás)
Synchronizers: a szálak közötti koordinációt segítő osztályok (Semaphor, Mutex, Barrier, Latch és Exchanger)
Locks: explicit lockolási lehetőségek
Nanosecond-granularity timing: nanoszekudumos pontosságú időmérés, időzítés lehetősége