Dal punto di vista del lock, questa classe e' del tutto equivalente alla sincronizzazione classica. Dichiarare un metodo synchronized equivale ad avere un membro lock della classe, una chiamata a lock.lock come prima istruzione del metodo ed una chiamata a lock.unlock come ultima.Con la sincronizzazione "classica" i metodi take() e put() sincronizzati, conferiscono all'oggetto che li contiene la sincronizzazione di tutto l'oggetto, questo perche' non ci sono altri metodi non sincronizzati.
D'altronde a me cosi' li hanno fatti studiare ed implementare in C, al corso di sistemi operativi, coi lock e le condition. E confesso di avere difficolta' ad usare la parola chiave synchronized... Forse perche' non mi ricordo mai come si scrive!
Quello che cambia qui e' che avendo due code, invece di una, il signal puo' selezionare quali thread svegliare e quali no.
Beh, piu' che in effecienza, e' il classico "baratto spazio-tempo": spreco un po' di memoria in piu' ma il programma (o quello che e', in generale. Anche nei PC moderni, gran parte dell' aumento di velocita' e' dovuto al fatto che ormai la memoria si butta, e ogni componente possiede notevoli quantita' di buffer) il programma, dicevo, ne guadagna in tempo di risposta.La sincronizzazione nel multithreading porta una certa ineficienza nell'esecuzione di un programma perche' un consumatore puo' trovarsi nella condizione di ottenere un lock piu' volte in maniera consecutiva ma non puo' inserire i dati cancellando quelli precedenti che non sono ancora stati consumati e quindi si ricorre ad un array di oggetti per fare in modo che quando un consumatore o un produttore si trova nella condizione di aver piu' volte consecutivamente un processore possa gestire la plus produzione o la plus consumazione.
Il problema non e' la sincronizzazione in se, ma il fatto che le entita', prese da sole, non sono sincronizzate (d'altronde se gia' lo erano, perche' sincronizzarle?)

Rispondi quotando