[ACCEPTED]-Proper way to use SyncLock (in general)-locking

Accepted answer
Score: 11

From the examples, it's hard to tell which 51 one is correct, if either is. A few guidelines/observations 50 though that might help you answer your question, or 49 know what to provide for additional information:

First 48 things first, do you have to synchronize? Would 47 it make more sense for each thread to have 46 an instance of this class? If each instance 45 is local to the thread, and is only modified 44 and used on that thread, you don't need 43 locking.

If the purpose of this class and 42 utilizing threads is for parallel processing 41 of a larger data set, it might make more 40 sense for the main thread to divide up the 39 task in some logical way, and then wait 38 for the worker threads to complete. In this 37 case, instead of managing threads on your 36 own, look into the ThreadPool and wait handles. Most 35 of the dirty work is done for you then.

About 34 synchronization/locking in general: If your 33 operation was interrupted between steps, would 32 the data be consistent/valid?

In your example, say 31 you have two threads. The first is in the 30 area between .AddRange() and .Count, when the second thread 29 comes along enters the function, and acquires 28 the lock on the list.

Thread 1 runs a bit 27 more, and hits the lock guarding the .Count method, and 26 goes to sleep. Thread 2 in the meantime 25 clears the list and then releases its lock, waking 24 Thread 1 up, which then acquires the lock.

In 23 this case, Thread 1 will have 0 returned 22 from this function, when work was done by 21 thread 1 to build the list. And then, the 20 list length won't really be 0, since thread 19 2 has come along and filled the list.

In 18 this case, the locks around the individual 17 list operations break the program, so it 16 makes more sense to have one lock surrounding 15 between Clear and the Count call.

In short, multi-threading 14 is a good way to introduce a whole class 13 of subtle bugs relating to Race Conditions, that often 12 result in Heisenbugs.

It is often wise to avoid threads 11 when you can. If you can't, try to arrange 10 your workload in ways that require minimal 9 synchronization (e.g. giving the thread 8 a set of data at the start, then waiting 7 for it to signal completion, such as with 6 the thread pool example linked). If you 5 can't do that, then tread carefully, and 4 always ask yourself "What will happen 3 if two threads run in this area".

Hopefully 2 this helps arm you for future adventures 1 in multi-threaded code.

Score: 7

"It depends". The two examples have different semantics.

In the latter example the 7 entire set of operations is atomic with respect to the lock. While in the former example access to 6 the list is guarded in lock, but the entire 5 set of operations can't be (correctly) viewed 4 as atomic (with respect to the lock).

Imagine what would/could happen 3 in terms if operation/thread interleaving 2 if ListWork was invoked upon the same object by different threads.

Happy 1 coding.

More Related questions