Framework: .net 4.5
I am using below sample code pattern to initialize variables in thread safe manner. Recently I have been reading some articles which explains 'double checked locking has been broken in some platforms http://www.cs.umd.edu/~pugh/java/memoryModel/DoubleCheckedLocking.html'. But looks like it's OK for me as I am using .net 4.5.
Recommendation as per the comments
Recommendation is to use lazy<T>
and let the .net framework do heavy lifting of handling thread safety and memory models based on platforms: http://msdn.microsoft.com/en-us/library/dd642331.aspx
Update
It appears Eric Lippert has been recommending not to use this pattern at all (now am confused) Name for this pattern? (Answer: lazy initialization with double-checked locking) C# manual lock/unlock
Update 2
Following excerpt is "Like all techniques that remove read locks, the code in Figure 7 (similar to the code I have) relies on strong write ordering. For example, this code would be incorrect in the ECMA memory model unless myValue was made volatile because the writes that initialize the LazyInitClass instance might be delayed until after the write to myValue, allowing the client of GetValue to read the uninitialized state. In the .NET Framework 2.0 model, the code works without volatile declarations." From http://msdn.microsoft.com/en-us/magazine/cc163715.aspx
And I am also not using 'volatile' as many examples showed in different code snippets. I am assuming it's OK too (reference: The need for volatile modifier in double checked locking in .NET )
Pseudo-code that explains the version I am using - built on top of .net 4.5:
static private object s_syncObject = new object();
private static string s_lazyInitializedVariable = null;
//is it necessar to make the backing varible volatie?
//private static volatile string s_lazyInitializedVariable = null;
private static string LazyInitializedVariable
{
get
{
if(string.IsNullOrWhiteSpace(s_lazyInitializedVariable))
{
lock(s_syncObject)
{
if (string.IsNullOrWhiteSpace(s_lazyInitializedVariable))
{
/*
* my lazy initialization code
*/
s_lazyInitializedVariable = "Initialized";
}
}
}
return s_lazyInitializedVariable;
}
}
I am seeking confirmation of the same. Basically below are my assumptions as I am using .net 4.5
Note: I also noticed that I can make use of lazy<T>
introduced in .net 4.0. but as of now will live with the way I am doing I guess, as I have seen the implementation of lazy<T>
using ILSpy, and looks like its doing relatively more stuff for simple tasks like mine.
Static initialization in the CLR is guaranteed to be thread-safe. Either of the following would be fine for thread-safe initialization:
static string s_lazyInitializedVariable = "Initialized";
If you want it lazy, just use the Lazy class:
static Lazy<string> s_lazyInitializedVariable = new Lazy<string>(() => "Initialized");
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With