The lock statement
Learn critical section protection with lock.
The lock statement
The lock statement protects a critical section. lock (_sync) { /* only one thread */ } lets only one thread enter at a time; others wait.
lock is a shortcut for Monitor.Enter and Monitor.Exit. The lock object is usually private readonly object _sync = new();; locking on this or a string is dangerous.
lock and atomicity
lock makes the code inside the block atomic; multiple threads cannot modify the same data at the same time. This prevents race conditions in operations like counter increment (counter++) or list appends.
lock is costly; for very small work, lighter alternatives such as Interlocked may be preferred. The right choice balances performance and safety.
Exercise Increment a counter with lock
Declare private static readonly object _sync = new object(); and private static int _counter = 0;. In Main create 2 threads, each calling lock (_sync) { _counter++; }. Wait with Join. Finally print Console.WriteLine($"Counter: {_counter}");. (2 threads * 1 increment = 2 expected.)
Show example solution
{_counter}");
Example solution:
using System;
using System.Threading;
class Program
{
private static readonly object _sync = new object();
private static int _counter = 0;
static void Main()
{
Thread t1 = new Thread(() => { lock (_sync) { _counter++; } });
Thread t2 = new Thread(() => { lock (_sync) { _counter++; } });
t1.Start();
t2.Start();
t1.Join();
t2.Join();
Console.WriteLine($"Counter: {_counter}");
}
}
Test yourself
-
Match the lock concepts
- lock (_sync)
- Critical section
- Monitor.Enter
- Basis of lock
- private readonly object _sync
- Lock object
- this (locking)
- Dangerous
-
Which object should lock use?
- private readonly object
- this
- string literal
- typeof(int)
Show answer
private readonly object — Correct. A private readonly object is the safest lock.
-
Complete the lock statement
____ (_sync) { counter++; }Show answer
lock (_sync) { counter++; }