[ NikolaVeber @ 04.01.2004. 11:52 ] @
Pozdrav !

U dilemi sam sto se tice razumevanja niti, tj nisam siguran da li sam stvari razumeo na pravi nacin, pa molim pomoc.

Predpostavimo da imam jednu public klasu i jos 2 pored nje, koje implementiraju Runnable. Te 2 klase rade isto sto i obicne klase, tj sasvim su normalne, sem sto umesto main() imaju run() i rade u nitima.

Razlika prilikom pozivanja "normalinih" i klasa koje impl. runnable je u tome sto u prvom slucaju imam new klasa1 i cekam da se zavrse sve metode koje su pozvane iz main() pre nego sto se izvrsi new klasa2, a prilikom
Code:

Runnable x = new Klasa1();
Thread nit1 = new Thread(x);
Runnable y = new Klasa2();
Thread nit2 = new Thread(x);

se te dve klase (tj njihove metode) izvrsavaju paralelno, ili kako je vec definisano odnosima izmedju niti.

Da li sam u pravu ?
[ Java Beograd @ 08.01.2004. 09:19 ] @
Hm ... Sudeci po konfuznosti pitanja, nista ti nije jasno. I prilicno gresis.
Ali, dobro, ja sam verovatno bio jos gori !

Znam da si stavio navodnike za "normalne" klase, ali moras i u nacinu razmisljanja da te klase shvatis kao normalne. (bez navodnika). Sve su klase normalne.

Implementacija Runnable interfejsa vodi do toga da se mora deklarisati public void run() metod. Deo koda koji se nalazi u toj metodi izvrsavace se paralelno sa izvrsavanjem nekog drugog koda.

Takodje vidim da mesas main() metod i konstruktor. Konstruktor nije main() !

U delu koda koji si naveo sve ce se metode izvrsavati linearno. Dakle, po zavrsetku prve linije ide se na drugu i tako redom. To sto klasa nasledjuje Runnable ne znaci da ce se njen konstruktor (inicijalizacija) izvrsavati u posebnom threadu. (Osim ako se iz konstruktora ne pozove start() )

Ajde, pitaj jos nesto, nisam siguran da li ti je jasnije.
[ weB_KiLeR @ 08.01.2004. 12:07 ] @
Imas ovde lep tutorial kako se radi sa thread-ovima...
http://www.oreilly.com/catalog/jthreads2/
Imas to objasnjeno i u mom tutorailu za sockete u javi.
[ NikolaVeber @ 08.01.2004. 12:29 ] @
Ok, posle sam citao o razlici izmedju main() i konstruktora.
Nego kada klasa implementira runnable, kada se napravi objekat te klase krece sa izvrsavanjem konstruktor. Kako da sada to smestim u novu nit ?
Odnosno, kako da pobegnem iz osnovne niti (u kojoj je zapocela izvrsavanja main() public klase)?
[ tweeester @ 08.01.2004. 13:23 ] @
Code:

Runnable x = new Klasa1();
Thread nit1 = new Thread(x);
nit1.start();       // Od ovog momenta x.run() se izvrsava paralelno sa ostatkom ovog koda
Runnable y = new Klasa2();
Thread nit2 = new Thread(x);
nit2.start();        // Sad postoji jos jedna nit ..... (tri ukupno, osim ako se nit1 vec nije zavrsila)
[ leka @ 08.01.2004. 13:47 ] @
Princip multithread programiranja je veoma prost. Kad se nit kreira ona radi nezavisno, totalno nezavisno, tako da tu nema price "pobegnem iz niti X u nit Y", ne postoji direktni mehanizam za tako nesto. Radi se o koncepciji, covek moze da "naredi" niti X da ceka da se nit Y zavrsi, moze da je zaustavi, moze da joj posalje signale, i slicno. Na ovaj nacin covek moze lako da sinhronizuje niti. Primera na NET-u imas na milione.
Dakle, ne postoji nacin da "skocis" iz niti X u nit Y. Konkurentno programiranje je poseban koncept, da bi to savladao moras malo da sednes, i lagano shvatis taj koncept. Ovako ces samo lutati u mraku...
[ NikolaVeber @ 08.01.2004. 16:38 ] @
Citao sam dosta o tome (smesno zvuci) i donekle razumem princip rada niti. Samo me zbunjuje njihova konkretna primena (profesionalna deformacija proceduralnog programera:D)
Moze li neki prost primer, "iz svakodnevnog zivota", gde je upotreba niti neophodna (ili bolja od njene neupotrebe)?
[ tweeester @ 08.01.2004. 16:58 ] @
Pa evo jedan primer iz relalnog zivota gde se koriste niti. Primer je neka aplikacija koja sadrzi par podsistema/modula (naprimer nekoliko klasa koje rade svaka svoj posao). Svaka od njih moze da ispali neke event-e koji su od interesa ostalim modulima. Event-e prima srce sistema (nazovimo ga kernel) koji ih smesta u queue (FIFO) i odmah se vraca iz funkcije da bi modul mogao nesmetano odmah da nastavi dalje. E sad tu u igru ulazi jedan low-priority thread koji event-e iz tog queue-a polako salje svim ostalim modulima na procesiranje. Prost primer ali nadam se da malo ilustruje potrebe za nitima
[ leka @ 08.01.2004. 17:12 ] @
U principu svaki client/server softver je bolje raditi pomocu niti. Najprostiji primer za ovu pricu je web server i web klijenti. Kad god se klijent uspesno konektuje na web server, ovaj kreira NIT koja ce da "usluzuje" klijenta, tj. da mu servira informacije.
Zasto je ovo bolje od nekog drugog nacina? - Zato jer je sam proces serviranja informacija klijentu X totalno nezavistan od serviranja informacija klijentu Y. I to je savrseno mesto gde treba koristiti niti. Drugo, niti su, kada covek gleda na resurse, "najjeftiniji" . Ne rezervisu mnogo prostora na heap-u i dele resurse medjusobno. Covek moze da kreira par hiljada niti koje nesto rade a da procesor i dalje "zivi"...
[ weB_KiLeR @ 08.01.2004. 20:47 ] @
Citat:
leka:
U principu svaki client/server softver je bolje raditi pomocu niti. Najprostiji primer za ovu pricu je web server i web klijenti. Kad god se klijent uspesno konektuje na web server, ovaj kreira NIT koja ce da "usluzuje" klijenta, tj. da mu servira informacije.
Zasto je ovo bolje od nekog drugog nacina? - Zato jer je sam proces serviranja informacija klijentu X totalno nezavistan od serviranja informacija klijentu Y. I to je savrseno mesto gde treba koristiti niti. Drugo, niti su, kada covek gleda na resurse, "najjeftiniji" . Ne rezervisu mnogo prostora na heap-u i dele resurse medjusobno. Covek moze da kreira par hiljada niti koje nesto rade a da procesor i dalje "zivi"...


Sto znaci da bez razumevanja thread-ova nema socket programiranja svaki iole slozeniji program moram imati niti kako bi na primer citao kroz socket i pisao u isto vreme... Ako ih nemas program ce da pukne ili da zablokira.
[ leka @ 09.01.2004. 03:17 ] @
Citat:
Sto znaci da bez razumevanja thread-ova nema socket
programiranja

Sa ovim se nikako ne bih slozio - ima na stotine hiljada mreznih
programa koji ne koriste niti. Umesto niti se forkuju procesi kada treba
da se usluzi klijent... Ovako se to radi(lo) godinama, a i danas danji
zato jer je sama stvar (mnogo) prostija nego rad sa nitima.
[ tweeester @ 09.01.2004. 08:49 ] @
Leka ocigledno nije javadzija (bez uvrede) Slazem se sa njegovim misljenjem kad je Linux u pitanju ali za Win i Java programiranje threads su jedini logican izbor.
[ NikolaVeber @ 09.01.2004. 18:55 ] @
Da li t oznaci da su na linuxu slabije performanse? Ili je samo u pitanju prednost linuxa?
[ dejankr @ 09.01.2004. 20:45 ] @
Kada se radi nešto u Javi, operativni sistem i platforma ne treba da budu važni (kod ne treba da bude specifičan za operativni sistem) pa mislim da pozivanje procesa ne treba da bude opcija kada se radi sa Javom. Tako da dodajem, da bez obzira koji operativni sistem/platforma se koristi ozbiljan JAVA program koji radi sa socketima nema smisla bez upotrebe niti.
Uostalom, SocketServer klasa koja se u Javi koristi pri radu sa Socketima blokira tekuću nit, a ako ne želiš da ti za to vreme cela aplikacija bude blokirana moraš da imaš makar još jednu nit. non-blocking konekcije su podržane tek od verzije 1.4, ali malo koji serverski program je pisan baš za Javu 1.4.

Na kraju krajeva programiranje sa nitima u Javi i nije neki problem u poređenju sa nekim starijim programskim jezicima, s obzirom da je podrška za niti ugrađena u sam jezik.
[ tweeester @ 13.01.2004. 10:32 ] @
Citat:
NikolaVeber:
Da li t oznaci da su na linuxu slabije performanse? Ili je samo u pitanju prednost linuxa?


Cisto informativno: Java thread je na Linux-u implementiran kao novi proces (logicno) a and Win kao novi thread.
[ sspasic @ 13.01.2004. 10:55 ] @
Pretpostavljam da si ovo zaključio na osnovu toga što se Java Thread pojavljuje u listi procesa na Linux-u. To je pre posledica načina na koji su niti implementirane na samom Linux-u (clone sistemski poziv). Ipak je bliže istini da je Java Thread na linux-u implementiran kao thread nego kao proces.
[ tweeester @ 13.01.2004. 11:54 ] @
Sasvim moguce ...
[ Dragi Tata @ 14.01.2004. 18:20 ] @
U principu, niti su na raznim operativnim sistemima različita stvar i zato je pomalo opasno koristiti neke "portabilne" biblioteke za rad sa nitima (Java, pthreads, Boost Threads) i smatrati da će tako napisani programi svuda da rade isto.

Uzgred, poslednji put kad sam proveravao Java nije imala podršku za thread pools u standardnoj biblioteci. Je li u međuvremenu urađeno nešto po tom pitanju?
[ dejankr @ 15.01.2004. 09:23 ] @
Citat:
Dragi Tata:
U principu, niti su na raznim operativnim sistemima različita stvar i zato je pomalo opasno koristiti neke "portabilne" biblioteke za rad sa nitima (Java, pthreads, Boost Threads) i smatrati da će tako napisani programi svuda da rade isto.

Uzgred, poslednji put kad sam proveravao Java nije imala podršku za thread pools u standardnoj biblioteci. Je li u međuvremenu urađeno nešto po tom pitanju?


Da se niti na različitim operativnim sistemima ne ponašaju potpuno isto - tu se slažem. Ipak, za stvari za koje se obično u Javi koirste niti mislim da nema nikakvih problema sa time i ne vidim zašto se ne bi koristile. Java vrši apstrakciju onoga što operativni sistem pruža, a sama JVM koja je specifična za svaki operativni sistem će obavljati "prljav posao".
Istina je da je rad sa nitima, ma koliko ga Java olakšala, i dalje prilično mukotrpan posao. Bagovi koji nastaju kao posledica nesinhronizacije pa i deadlockovi se jako teško otkrivaju, i dešava se da aplikacija radi nedeljama i mesecima dok se problem ne ispolji. Ipak za mnoge probleme nema izbora, tako da na primer rad sa servletima podrazumeva da pišete thread safe kod.

A što se tiče thread pool-ova oni još uvek nisu deo JDK. Mada mi se čini da sam čuo da će Tiger (JDK 1.5) uključiti i thread poolove i neke druge korisne stvari za rad sa nitima.
[ NikolaVeber @ 15.01.2004. 12:12 ] @
Znaci li to da upotreba niti nije neophodna za "dobro" programiranje u javi. Pod dobrim podrazumevam neki prosek elegancije, performansi it.d.
[ dejankr @ 15.01.2004. 13:41 ] @
Citat:
NikolaVeber:
Znaci li to da upotreba niti nije neophodna za "dobro" programiranje u javi. Pod dobrim podrazumevam neki prosek elegancije, performansi it.d.


Java je jezik opšte namene što znači da se može koristiti za sve i svašta. Ne postoji tipičan ili prosečan Java program jer dok neko Javu koristi za pravljenje klijentskih aplikacije za grafičkim interfejsom drugi ga koriste za pisanje servleta ili EJB ili uopšte nekih serverskih programa koji nemaju GUI, da ne pominjem rad sa J2ME, JavaCard i slično. Znači ono "dobro programiranje" nema mnogo smisla jer se pojedini programi u Javi mogu porediti kao babe i žabe.

S druge strane, ako želiš da se ozbiljno baviš Javom onda višenitno programiranje moraš da razumeš. Da li ćeš niti koirsititi direktno ili indirektno (i koliko ćeš ih koristiti uopšte) zavisi on vrste programa koje ćeš da praviš ali pre ili kasnije ćeš naići na njih. Niti su u Javi ugrađene u sam jezik, postoji par ključnih koje su uvedene zbog niti, svaka knjiga o Javi ili Java tutorijal se bavi i njima - to nije bez razloga.

Dejan
[ Dragi Tata @ 15.01.2004. 16:49 ] @
Citat:
dejankr:
Da se niti na različitim operativnim sistemima ne ponašaju potpuno isto - tu se slažem. Ipak, za stvari za koje se obično u Javi koirste niti mislim da nema nikakvih problema sa time i ne vidim zašto se ne bi koristile. Java vrši apstrakciju onoga što operativni sistem pruža, a sama JVM koja je specifična za svaki operativni sistem će obavljati "prljav posao".


Govorim o npr sledećem: Niti su u Windowsu i Linuxu kernel objekti i ako kreiraš više niti na višeprocesorskoj mašini, onda će takva aplikacija da radi brže nego na mašini sa jednim procesorom ("skalira"). Međutim, na FreeBSD-u, niti su user-mode objekti (ako ćemo da cepidlačimo, postoji funkcija rfork koja pravi i kernel-mode niti, ali POSIX threads funkcije koliko znam koriste user-mode niti, a verujem da JVM poziva te funkcije a ne rfork) i možeš da dodaješ koliko hoćeš procesora - ništa ti ne vredi. Dakle, isti program pisan u Javi ili npr C++u sa Boost threads bibliotekom će na Windowsu skalirati, a na FreeBSD-u neće.

Poenta ovog mog mudrovanja je da kad su niti u pitanju često ne smemo slepo verovati portabilnim bibliotekama, već moramo znati šta se dešava ispod haube.
[ sspasic @ 15.01.2004. 18:16 ] @
Moram da se sa ovim ne složim do kraja. Ako sam dobro zaključio, kažeš da program koji koristi user-mode niti skalira slabije od onog koji koristi kernel-mode.

To ne mora da bude tako. To što se sve niti izvršavaju u istom procesu ne mora da bude problem ako na tom kompjuteru ostali procesi ne troše mnogo vremena. Ponašanje tog procesa se na svim Unix-ima, pa pretpostavljam i na FreeBSD-u, može dodatno štelovati pomoću štelovanja 'nice value'.

Prema nekom mom iskustvu, programi koji koriste user-mode niti mogu da skaliraju drastično bolje (subjektivno iskustvo, nisam mnogo merio) ako ima puno niti i puno sinhronizacije među njima. Ovo je uglavnom zato što se izbegava većina skokova user mode/kernel mode.

Što se tiče Jave na Linux-u, do pre par verzija je postojao switch koji je birao sa kakvim se mehanizmom za niti podiže program (native/green).
A verujem da će novi 2.6 kernel ovde drastično da promeni odnos kada je koji mehanizam bolji od onog drugog, jer je jedna od ključnih novosti upravo brža implementacija pthreads.
[ sspasic @ 15.01.2004. 18:20 ] @
Sorry - sad vidim da si mislio na skaliranje kad se dodaje više procesora :) Tu si u pravu.
Ja sam mislio na skaliranje u odnosu na broj niti.
[ dejankr @ 16.01.2004. 09:13 ] @
Citat:
Dragi Tata:
Citat:
dejankr:
Da se niti na različitim operativnim sistemima ne ponašaju potpuno isto - tu se slažem. Ipak, za stvari za koje se obično u Javi koirste niti mislim da nema nikakvih problema sa time i ne vidim zašto se ne bi koristile. Java vrši apstrakciju onoga što operativni sistem pruža, a sama JVM koja je specifična za svaki operativni sistem će obavljati "prljav posao".


Govorim o npr sledećem: Niti su u Windowsu i Linuxu kernel objekti i ako kreiraš više niti na višeprocesorskoj mašini, onda će takva aplikacija da radi brže nego na mašini sa jednim procesorom ("skalira"). Međutim, na FreeBSD-u, niti su user-mode objekti (ako ćemo da cepidlačimo, postoji funkcija rfork koja pravi i kernel-mode niti, ali POSIX threads funkcije koliko znam koriste user-mode niti, a verujem da JVM poziva te funkcije a ne rfork) i možeš da dodaješ koliko hoćeš procesora - ništa ti ne vredi. Dakle, isti program pisan u Javi ili npr C++u sa Boost threads bibliotekom će na Windowsu skalirati, a na FreeBSD-u neće.

Poenta ovog mog mudrovanja je da kad su niti u pitanju često ne smemo slepo verovati portabilnim bibliotekama, već moramo znati šta se dešava ispod haube.


Ne razumem se preterano u implementaciju niti na pojedinim operativnim sistemima (ja sam pre svega aplikativac) ali recimo da si u pravu. Međutim, poenta onog što sam ja hteo da kažem jeste da Javu ljudi koriste između ostalog zato što je portabilna. Ja razvijam programe na Windowsu 2000 a u produkciji su mi na RH Linuxu 8 i ne moram da menjam ni jedan red koda. Da Java aplikacije imaju različite performanse na različitim operativnim sistemima i platformama uopšte - to je poznata stvar i to zavisi od mnogo stvari, neke su vezane za sam operativni sistem a neke su vezane za implementaciju JVM na tom operativnom sistemu (svi znaju da je JRockit brži od Sun JVM).
Ipak, to su stvari koje se tolerišu jer imaju malo značaja za samu aplikaciju - tj. Java kod se po pravilu ne prilagođava pojedinoj platformi - to je posao JVM. Ne postoji Tomcat za Linux i Tomcat za Windows - postoji samo Tomcat koji možeš da koristiš na svim platformama. Da ne pričam o web aplikacijama koje se izvršavaju u okviru Tomcata.

Isto važi i za niti. To je deo jezika Java (više nego na primer I/O) i pre ili kasnije moraš da ih koristiš. I ako već koristiš Javu, koristiš ih na isti način za sve platforme - tj. u sklopu onoga što ti garantuje sama Java. Ako već hoćeš da pišeš kod koji je specifičan za platformu onda Java možda i nije pravo rešenje.

Znači, ne poričem ništa od ovog što si rekao, samo naglašavam da kada se radi u Javi najčešće se ne vezuješ za određeni operativni sistem.