I have been reading several articles on threading in C# and mostly am looking for confirmation that I understand how it is working so that I do not cause unexpected behavior in the application I am developing.
So given the example below, I have a few questions.
- The main thread which the application is running sets the shared string to "123". It is guaranteed that the spawned off threads #2 and #3 will not return 000 when calling
ConvertToNumber()
because the main thread sets the string to "123" before any of those other threads are spawned. Correct? - Thread #4 is guaranteed to return 789 when calling
ConvertToNumber()
because the string is set to "789" in at least the core's local cache and possibly in higher levels of memory such as main memory. Correct? - Assume threads #2, #3, and #4 are currently running and thread #4 reaches the assignment of "789" before #2 and #3 execute
ConvertToNumber()
. Threads #2 and #3 then reachConvertToNumber()
. It is not guaranteed that they will return 789 because the core running those thread could have the local cached value of the string "123". Correct?
Assuming that what I stated above is indeed correct, would specifying SharedString
as volatile
be a valid fix? Is that the intended usage of volatile
? Would also wrapping the Convert.ToInt32(SharedString)
with a lock also fix the issue and if so, which is the prefered method - lock or volatile?
public static class ExampleClass
{
public static string SharedString { get; set; } = "000";
public static int ConvertToNumber()
{
return Convert.ToInt32(SharedString);
}
}
//Main thread (thread #1)
ExampleClass.SharedString = "123";
//After setting string to "123", The following code happens in different spawned off threads running concurrently.
//thread (thread #2) is created and does the following
//...some code stuff...
ExampleClass.ConvertToNumber();
//thread (thread #3) is created and does the following
//...some code stuff...
ExampleClass.ConvertToNumber();
//thread (thread #4) is created and does the following
//...some code stuff...
ExampleClass.SharedString = "789";
ExampleClass.ConvertToNumber();