简体   繁体   中英

why lock tokens are needed for multithreading programs

Below is an example

public class Printer
{
    // Lock token.
    private object threadLock = new object();
    public void PrintNumbers()
    {
       // Use the lock token.
       lock (threadLock)
       {
           ...
       }
    }
}

but I still don't get the concept of a thread token, why is it necessary? is a thread token same thing as Semaphore in C? But for C programs, a Semaphore is just a integer?

lock is a mutex, and works like POSIX pthread_mutex_lock and pthread_mutex_unlock in C.

Only one piece of code is allowed to acquire a lock on a given object at once, so it's a way of synchronizing threads (not necessarily the best way, but that's a much more detailed and highly contextual answer).


As an example, the following code runs a couple threads at the same time:

  • one increments each element of an array of numbers by 10,
  • the other prints the contents of the array
var numbers = new int[] { 1, 2, 3, 4, 5, 6, 7, 8, 9, 10 };

Task.WhenAll(
  Task.Run(() =>
  {
    for (var i = 0; i < 10; i++)
    {
      numbers[i] += 10;
      Thread.Sleep(10);
    }
  }),
  Task.Run(() =>
  {
    foreach (var i in numbers)
    {
      Console.Write(i + " ");
      Thread.Sleep(10);
    }
  })
);

Since they run at the same time, the output is something like:

11 2 13 4 5 6 7 18 9 10

Some numbers are incremented, others are not, and it's different every time.

The same code with the loops wrapped in a lock, however:

object threadLock = new object();
var numbers = new int[] { 1, 2, 3, 4, 5, 6, 7, 8, 9, 10 };

Task.WhenAll(
  Task.Run(() =>
  {
    lock (threadLock)
    {
      for (var i = 0; i < 10; i++)
      {
        numbers[i] += 10;
        Thread.Sleep(10);
      }
    }
  }),
  Task.Run(() =>
  {
    lock (threadLock)
    {
      foreach (var i in numbers)
      {
        Console.Write(i + " ");
        Thread.Sleep(10);
      }
    }
  })
);

This only ever outputs one of the two things, depending on which loop acquires the lock first:

11 12 13 14 15 16 17 18 19 20

or

1 2 3 4 5 6 7 8 9 10

There's no actual coordination between the two tasks, so which set you get (incremented or not) just depends on which happens to acquire the lock first.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM