Originariamente inviato da dekorus
non capisco a chi passa il controllo??
passa al thread che era in wait o resta a quello che ha fatto la signal?
Innanzitutto una premessa (che forse, spero, sai già). Un thread può invocare wait()/notify()/notifyAll() solo su un oggetto di cui ha acquisito il lock. Pertanto questa invocazione deve essere in un contesto "synchronized", ovvero dentro un metodo o blocco synchronized in cui si acquisce il lock sull'oggetto.
Codice del wait:
codice:
synchronized(obj) {
...
obj.wait();
...
}
Codice del notify:
codice:
synchronized(obj) {
...
obj.notify();
...
}
Ipotizziamo 2 thread A e B e immaginiamo che sull'oggetto referenziato da obj non sia stato acquisito il lock da nessun thread.
Il thread A entra nel blocco synchronized (acquisendo il lock) ed invoca il wait(). Il wait() causa 2 effetti: a) Il thread A viene subito tolto dallo stato di "running" e messo in uno stato di "wait" b) Il thread A rilascia il lock sull'oggetto.
Successivamente il thread B entra nell'altro blocco synchronized. Supponendo nessun altro abbia acquisito il lock, può farlo perché A l'aveva rilasciato. Ed esegue il notify().
Questo non causa automaticamente la continuazione della esecuzione di A e non causa direttamente alcuna sospensione di B.
Il thread B può continuare la sua esecuzione, per quanto tempo ..... beh, dipende dallo scheduler.
Quello che è importante capire è che il thread A deve riacquisire il lock sull'oggetto per poter continuare (è in un blocco synchronized, no?). E questo può avvenire solo quando il thread B rilascia il lock, ovvero uscendo dal blocco synchronized.
In sostanza: il thread A viene tolto dallo stato di wait ma deve comunque "competere" con B per avere il lock sull'oggetto. Appena B rilascia il lock, allora A può riacquisirlo e quindi tornare in stato "runnable" e successivamente, quando scelto dallo scheduler, tornare in "running".