1. Perché chiudere e cosa è chiuso?
Quando usiamo thread, il modo più efficiente è ovviamente asincrono, cioè ogni thread viene eseguito contemporaneamente, senza dipendere dagli altri e aspettare. Tuttavia, quando thread diversi devono accedere a una certa risorsa, è necessario un meccanismo di sincronizzazione, cioè, quando si legge e si scrive la stessa risorsa, è necessario far sì che la risorsa sia gestita solo da un thread contemporaneamente per garantire che ogni operazione sia efficace e immediata, cioè per garantire l'atomicità del suo funzionamento. lock è il metodo di sincronizzazione più comunemente usato in C#, nel formato lock(objectA){codeB}.
lock(objectA){codeB} sembra semplice, ma in realtà ha tre significati, essenziali per usarlo correttamente: 1. L'oggetto A è bloccato? Se no, lo blocco, altrimenti aspetto che venga rilasciato l'oggetto A. 2. Dopo il blocco, gli altri thread non possono chiamare codeB né usare l'oggetto A durante l'esecuzione di codeB. 3. Dopo aver eseguito codeB, rilascia l'oggetto A, e codeB può essere accessibile da altri thread.
2. Che fine ha fatto la serratura?
Vediamo un esempio:
Nel thread t1, LockMe chiama lock(this), cioè c1 nella funzione principale, e quando chiama lock(c1) nel thread principale, deve aspettare che il blocco lock in t1 venga eseguito prima di accedere a c1, cioè tutte le operazioni correlate a c1 non possono essere completate, quindi vediamo che anche c1. DoNotLockMe() non viene eseguito.
|