Suppose I have singleton class that acts as a data cache. Multiple threads will read from the cache, and a single thread will periodically refresh it. It looks something like this:
public sealed class DataStore
{
public static DataStore Instance { get { return _instance; } }
public Dictionary<Foo, Bar> FooBar { get; private set; }
static DataStore() { }
private DataStore() { }
public void Refresh() {
FooBar = GetFooBarFromDB();
}
private static readonly DataStore _instance = new DataStore();
}
My question is essentially, is it safe to Refresh()
while other threads may be accessing FooBar
? Do I need to be using locks, or are my getting and setting operations atomic? Do I need to explicitly declare volatile
fields to back up my properties?
P.S., If someone can think of a more descriptive title for this question, I would gladly welcome it.
Edit: Fixed my example to correct obviously non-atomic code.
Instance
. Simply make_instance
public. (3) IMHO, no, this is not thread safe. - Andre CalilInstance
is read-only. Making the_instance
public will change it to writeable - zerkms{ get; private set; }
, right? - Andre CalilFooBar
value.) Or do you mean "will this do what I indend it to do?" (Impossible to tell from this little information.) Thread safety isn't a matter of "using thread safe classes" or "putting locks around all shared data" (which would work but might be terrible for performance), it's a matter of having the correct (desired) behaviour in the face of concurrency. - millimooseDictionary
to other classes / threads, and instead let them work over either point-in-time snapshots; or if you don't need consistent snapshots, the enumerator of aConcurrentDictionary
. (Of course you then need to make sure clients can't or won't mutate the objects stored in the dictionary.) - millimoose