semplificato la questione di dare una rappresentazione più chiara di quello che sto chiedendo in realtàarray di oggetti, l'aggiornamento in un thread e la lettura in un altro
Ho due fili, li chiamano A
e B
. Condivide un oggetto di tipo Foo
che ha un campo chiamato Name
e viene memorizzato in un array di tipo Foo[]
all'indice 0
. I thread accedono sempre all'indice 0
in un ordine che è già garantito dal sistema, quindi non esiste alcuna condizione di competizione della filettatura B
preceduta dal thread A
.
L'ordine è questo.
// Thread A
array[0].Name = "Jason";
// Thread B
string theName = array[0].Name
Come ho detto questo ordine è già garantito, non c'è modo per filo B per leggere il valore prima di infilare un
Quello che voglio garantire è di due cose:
- Entrambi i thread ottengono l'ultimo oggetto all'indice 0.
- Il thread
B
ottiene sempre l'ultimo valore nel campo .Name
La marcatura di Name
come volatile non è un'opzione, in quanto gli oggetti reali sono molto più complessi e dispongono anche di strutture personalizzate che non possono nemmeno avere l'attributo volatile ad essi collegato.
Ora, soddisfacendo 1 è facile (ottenendo sempre l'ultimo oggetto), si può fare un .VolatileRead:
// Thread A
Foo obj = (Foo)Thread.VolatileRead(ref array[0]);
obj.Name = "Jason";
// Thread B
Foo obj = (Foo)Thread.VolatileRead(ref array[0]);
string theName = obj.Name
Oppure è possibile inserire una barriera di memoria:
// Thread A
array[0].Name = "Jason";
Thread.MemoryBarrier();
// Thread B
Thread.MemoryBarrier();
string theName = array[0].Name
Quindi la mia domanda è: è sufficiente per soddisfare anche la condizione 2? Che ottengo sempre l'ultimo valore dai campi dell'oggetto che ho letto? Se l'oggetto nell'indice 0
non è cambiato, ma lo è Name
. Effettuando un VolatileRead
o un 0
sull'indice , assicurarsi che tutti i campi nell'oggetto all'indice 0
ottengano anche i loro ultimi valori?
Perché stai usando gli array? Guarda lo spazio dei nomi ['System.Collections.Concurrent'] (http://msdn.microsoft.com/en-us/library/system.collections.concurrent.aspx). – Oded
Non usando .NET4, per cominciare. E le cose Concurrent, per quanto ne so, non fanno che garantire il contenuto delle collezioni stesse e non i possibili campi/proprietà degli oggetti nelle collezioni. – thr
Non penso che volatile garantirebbe quello che pensi che sarebbe. –