Π§ΠΈΡ‚Π°ΠΉΡ‚Π΅ ΠΊΠ½ΠΈΠ³ΠΈ ΠΎΠ½Π»Π°ΠΉΠ½ Π½Π° Bookidrom.ru! БСсплатныС ΠΊΠ½ΠΈΠ³ΠΈ Π² ΠΎΠ΄Π½ΠΎΠΌ ΠΊΠ»ΠΈΠΊΠ΅

Π§ΠΈΡ‚Π°Ρ‚ΡŒ ΠΎΠ½Π»Π°ΠΉΠ½ Β«Π―Π—Π«Πš ΠŸΠ ΠžΠ“Π ΠΠœΠœΠ˜Π ΠžΠ’ΠΠΠ˜Π― Π‘# 2005 И ΠŸΠ›ΠΠ’Π€ΠžΠ ΠœΠ .NET 2.0. 3-Π΅ ΠΈΠ·Π΄Π°Π½ΠΈΠ΅Β». Π‘Ρ‚Ρ€Π°Π½ΠΈΡ†Π° 127

Автор Π­Π½Π΄Ρ€ΡŽ ВроСлсСн

Π—Π°ΠΌΠ΅Ρ‡Π°Π½ΠΈΠ΅. Если ΠΏΡ‹Ρ‚Π°Ρ‚ΡŒΡΡ Π±Π»ΠΎΠΊΠΈΡ€ΠΎΠ²Π°Ρ‚ΡŒ ΠΏΡ€ΠΎΠ³Ρ€Π°ΠΌΠΌΠ½Ρ‹ΠΉ ΠΊΠΎΠ΄ Π² статичСском ΠΌΠ΅Ρ‚ΠΎΠ΄Π΅, Π²Ρ‹, ΠΎΡ‡Π΅Π²ΠΈΠ΄Π½ΠΎ, Π½Π΅ ΠΌΠΎΠΆΠ΅Ρ‚Π΅ ΠΈΡΠΏΠΎΠ»ΡŒΠ·ΠΎΠ²Π°Ρ‚ΡŒ ΠΊΠ»ΡŽΡ‡Π΅Π²ΠΎΠ΅ слово this. Но Π² этом случаС ΠΌΠΎΠΆΠ½ΠΎ ΠΏΠ΅Ρ€Π΅Π΄Π°Ρ‚ΡŒ ΠΎΠ±ΡŠΠ΅ΠΊΡ‚ System.Type ΡΠΎΠΎΡ‚Π²Π΅Ρ‚ΡΡ‚Π²ΡƒΡŽΡ‰Π΅Π³ΠΎ класса с ΠΏΠΎΠΌΠΎΡ‰ΡŒΡŽ ΠΎΠΏΠ΅Ρ€Π°Ρ‚ΠΎΡ€Π° C# typeof.

Если снова Π²Ρ‹ΠΏΠΎΠ»Π½ΠΈΡ‚ΡŒ это ΠΏΡ€ΠΈΠ»ΠΎΠΆΠ΅Π½ΠΈΠ΅, Π²Ρ‹ ΡƒΠ²ΠΈΠ΄ΠΈΡ‚Π΅, Ρ‡Ρ‚ΠΎ Ρ‚Π΅ΠΏΠ΅Ρ€ΡŒ ΠΊΠ°ΠΆΠ΄Ρ‹ΠΉ ΠΏΠΎΡ‚ΠΎΠΊ ΠΏΠΎΠ»ΡƒΡ‡Π°Π΅Ρ‚ Π²ΠΎΠ·ΠΌΠΎΠΆΠ½ΠΎΡΡ‚ΡŒ Π·Π°ΠΊΠΎΠ½Ρ‡ΠΈΡ‚ΡŒ свою Ρ€Π°Π±ΠΎΡ‚Ρƒ (рис. 14.10).

Рис. 14.10. ΠšΠΎΠ½ΠΊΡƒΡ€Π΅Π½Ρ†ΠΈΡ Π² дСйствии, Ρ‚Ρ€Π΅Ρ‚ΡŒΡ ΠΏΠΎΠΏΡ‹Ρ‚ΠΊΠ°

Π˜ΡΡ…ΠΎΠ΄Π½Ρ‹ΠΉ ΠΊΠΎΠ΄. ΠŸΡ€ΠΎΠ΅ΠΊΡ‚ MultiThreadedPrinting Ρ€Π°Π·ΠΌΠ΅Ρ‰Π΅Π½ Π² ΠΏΠΎΠ΄ΠΊΠ°Ρ‚Π°Π»ΠΎΠ³Π΅, ΡΠΎΠΎΡ‚Π²Π΅Ρ‚ΡΡ‚Π²ΡƒΡŽΡ‰Π΅ΠΌ Π³Π»Π°Π²Π΅ 14.

Бинхронизация с ΠΏΠΎΠΌΠΎΡ‰ΡŒΡŽ Ρ‚ΠΈΠΏΠ° System.Threading.Monitor

ΠžΠΏΠ΅Ρ€Π°Ρ‚ΠΎΡ€ C# lock Π½Π° самом Π΄Π΅Π»Π΅ являСтся лишь ΠΊΠ»ΡŽΡ‡Π΅Π²Ρ‹ΠΌ словом, ΠΎΠ±ΠΎΠ·Π½Π°Ρ‡Π°ΡŽΡ‰ΠΈΠΌ использованиС Ρ‚ΠΈΠΏΠ° класса System.Threading.Monitor. ПослС ΠΎΠ±Ρ€Π°Π±ΠΎΡ‚ΠΊΠΈ компилятором C# контСкст Π±Π»ΠΎΠΊΠΈΡ€ΠΎΠ²ΠΊΠΈ прСвращаСтся Π² ΡΠ»Π΅Π΄ΡƒΡŽΡ‰Π΅Π΅ (Π²Ρ‹ ΠΌΠΎΠΆΠ΅Ρ‚Π΅ ΡƒΠ±Π΅Π΄ΠΈΡ‚ΡŒΡΡ Π² этом с ΠΏΠΎΠΌΠΎΡ‰ΡŒΡŽ ildasm.exe).

public void PrintNumbers() {

 Monitor.Enter(this);

 try {

  // Π’Ρ‹Π·ΠΎΠ² ΠΈΠ½Ρ„ΠΎΡ€ΠΌΠ°Ρ†ΠΈΠΈ Thread.

  Console.WriteLine("-β€Ί {0} выполняСт PrintNumbers()", Thread.CurrentThread.Name); // Π’Ρ‹Π²ΠΎΠ΄ чисСл.

  Console.Write("Π’Π°ΡˆΠΈ числа: ");

  for (int i = 0; i β€Ή 10; i++) {

   Random r = new Random();

   Thread.Sleep(1000* r.Next(5));

   Console.Write(i + ", ");

  }

  Console.WriteLine();

 } finallΡƒ {

  Monitor.Exit(this);

 }

}

Π’ΠΎ-ΠΏΠ΅Ρ€Π²Ρ‹Ρ…, Π·Π°ΠΌΠ΅Ρ‚ΠΈΠΌ, Ρ‡Ρ‚ΠΎ ΠΊΠΎΠ½Π΅Ρ‡Π½Ρ‹ΠΌ ΠΏΠΎΠ»ΡƒΡ‡Π°Ρ‚Π΅Π»Π΅ΠΌ ΠΌΠ°Ρ€ΠΊΠ΅Ρ€Π° ΠΏΠΎΡ‚ΠΎΠΊΠ°, ΠΊΠΎΡ‚ΠΎΡ€Ρ‹ΠΉ Π±Ρ‹Π» ΡƒΠΊΠ°Π·Π°Π½ Π² качСствС Π°Ρ€Π³ΡƒΠΌΠ΅Π½Ρ‚Π° ΠΊΠ»ΡŽΡ‡Π΅Π²ΠΎΠ³ΠΎ слова lock, являСтся ΠΌΠ΅Ρ‚ΠΎΠ΄ Monitor.Enter(). Π’ΠΎ-Π²Ρ‚ΠΎΡ€Ρ‹Ρ…, вСсь ΠΏΡ€ΠΎΠ³Ρ€Π°ΠΌΠΌΠ½Ρ‹ΠΉ ΠΊΠΎΠ΄ Π² Ρ€Π°ΠΌΠΊΠ°Ρ… контСкста ΡΠΎΠΎΡ‚Π²Π΅Ρ‚ΡΡ‚Π²ΡƒΡŽΡ‰Π΅ΠΉ Π±Π»ΠΎΠΊΠΈΡ€ΠΎΠ²ΠΊΠΈ ΠΏΠΎΠΌΠ΅Ρ‰Π΅Π½ Π² Π±Π»ΠΎΠΊ try. Π‘ΠΎΠΎΡ‚Π²Π΅Ρ‚ΡΡ‚Π²ΡƒΡŽΡ‰ΠΈΠΉ Π±Π»ΠΎΠΊ finally Π³Π°Ρ€Π°Π½Ρ‚ΠΈΡ€ΡƒΠ΅Ρ‚, Ρ‡Ρ‚ΠΎ ΠΌΠ°Ρ€ΠΊΠ΅Ρ€ ΠΏΠΎΡ‚ΠΎΠΊΠ° Π±ΡƒΠ΄Π΅Ρ‚ освобоТдСн (с ΠΏΠΎΠΌΠΎΡ‰ΡŒΡŽ ΠΌΠ΅Ρ‚ΠΎΠ΄Π° Monitor.Exit()), нСзависимо ΠΎΡ‚ ΠΈΡΠΊΠ»ΡŽΡ‡Π΅Π½ΠΈΠΉ, ΠΊΠΎΡ‚ΠΎΡ€Ρ‹Π΅ ΠΌΠΎΠ³ΡƒΡ‚ Π²ΠΎΠ·Π½ΠΈΠΊΠ°Ρ‚ΡŒ Π² срСдС выполнСния. Если ΠΈΠ·ΠΌΠ΅Π½ΠΈΡ‚ΡŒ ΠΏΡ€ΠΎΠ³Ρ€Π°ΠΌΠΌΡƒ MultiThreadSharedData Ρ‚Π°ΠΊ, Ρ‡Ρ‚ΠΎΠ±Ρ‹ Ρ‚ΠΈΠΏ Monitor использовался нСпосрСдствСнно (ΠΊΠ°ΠΊ это Π±ΡƒΠ΄Π΅Ρ‚ сдСлано Ρ‡ΡƒΡ‚ΡŒ ΠΏΠΎΠ·ΠΆΠ΅), Ρ‚ΠΎ Π΅Π΅ Π²Ρ‹Π²ΠΎΠ΄ останСтся Ρ‚Π΅ΠΌ ΠΆΠ΅.

ΠŸΡ€ΠΈ использовании ΠΊΠ»ΡŽΡ‡Π΅Π²ΠΎΠ³ΠΎ слова lock, каТСтся, трСбуСтся мСньший Π²Π²ΠΎΠ΄ ΠΏΡ€ΠΎΠ³Ρ€Π°ΠΌΠΌΠ½ΠΎΠ³ΠΎ ΠΊΠΎΠ΄Π°, Ρ‡Π΅ΠΌ ΠΏΡ€ΠΈ явном использований Ρ‚ΠΈΠΏΠ° System.Threading.Monitor, поэтому Π²Ρ‹ ΠΌΠΎΠΆΠ΅Ρ‚Π΅ Π·Π°Π΄Π°Ρ‚ΡŒ вопрос ΠΎ прСимущСствах нСпосрСдствСнного использования Ρ‚ΠΈΠΏΠ° Monitor. ΠšΡ€Π°Ρ‚ΠΊΠΈΠΉ ΠΎΡ‚Π²Π΅Ρ‚: ΠΊΠΎΠ½Ρ‚Ρ€ΠΎΠ»ΡŒ. ΠŸΡ€ΠΈ использовании Ρ‚ΠΈΠΏΠ° Monitor Π²Ρ‹ ΠΌΠΎΠΆΠ΅Ρ‚Π΅ Π΄Π°Ρ‚ΡŒ ΡƒΠΊΠ°Π·Π°Π½ΠΈΠ΅ Π°ΠΊΡ‚ΠΈΠ²Π½ΠΎΠΌΡƒ ΠΏΠΎΡ‚ΠΎΠΊΡƒ ΠΏΠΎΠ΄ΠΎΠΆΠ΄Π°Ρ‚ΡŒ (с ΠΏΠΎΠΌΠΎΡ‰ΡŒΡŽ ΠΌΠ΅Ρ‚ΠΎΠ΄Π° Wait()), ΠΈΠ½Ρ„ΠΎΡ€ΠΌΠΈΡ€ΠΎΠ²Π°Ρ‚ΡŒ ΠΎΠΆΠΈΠ΄Π°ΡŽΡ‰ΠΈΠ΅ ΠΏΠΎΡ‚ΠΎΠΊΠΈ ΠΎ Π·Π°Π²Π΅Ρ€ΡˆΠ΅Π½ΠΈΠΈ Ρ‚Π΅ΠΊΡƒΡ‰Π΅Π³ΠΎ ΠΏΠΎΡ‚ΠΎΠΊΠ° (с ΠΏΠΎΠΌΠΎΡ‰ΡŒΡŽ ΠΌΠ΅Ρ‚ΠΎΠ΄ΠΎΠ² Pulse() ΠΈ PulseAll()) ΠΈ Ρ‚.Π΄.

Π’ Π±ΠΎΠ»ΡŒΡˆΠΈΠ½ΡΡ‚Π²Π΅ случаСв Π²Π°ΠΌ Π±ΡƒΠ΄Π΅Ρ‚ Π²ΠΏΠΎΠ»Π½Π΅ достаточно возмоТностСй, обСспСчиваСмых ΠΊΠ»ΡŽΡ‡Π΅Π²Ρ‹ΠΌ словам C# lock. Но Ссли Π²Ρ‹ Π·Π°Ρ…ΠΎΡ‚ΠΈΡ‚Π΅ Ρ€Π°ΡΡΠΌΠΎΡ‚Ρ€Π΅Ρ‚ΡŒ Π΄Ρ€ΡƒΠ³ΠΈΠ΅ Ρ‡Π»Π΅Π½Ρ‹ класса Monitor, ΠΎΠ±Ρ€Π°Ρ‚ΠΈΡ‚Π΅ΡΡŒ ΠΊ Π΄ΠΎΠΊΡƒΠΌΠ΅Π½Ρ‚Π°Ρ†ΠΈΠΈ .NET Framework 2.0 SDK.

Бинхронизация с ΠΏΠΎΠΌΠΎΡ‰ΡŒΡŽ Ρ‚ΠΈΠΏΠ° System.Threading.Interlocked

Π’ это всСгда вСрится с Ρ‚Ρ€ΡƒΠ΄ΠΎΠΌ, ΠΏΠΎΠΊΠ° Π²Ρ‹ Π½Π΅ ΠΏΡ€ΠΎΠ²Π΅Ρ€ΠΈΡ‚Π΅ ΡΠΎΠΎΡ‚Π²Π΅Ρ‚ΡΡ‚Π²ΡƒΡŽΡ‰ΠΈΠΉ ΠΏΡ€ΠΎΠ³Ρ€Π°ΠΌΠΌΠ½Ρ‹ΠΉ ΠΊΠΎΠ΄ CIL, Π½ΠΎ ΠΈ ΠΎΠΏΠ΅Ρ€Π°Ρ†ΠΈΠΈ присваивания, ΠΈ Π±Π°Π·ΠΎΠ²Ρ‹Π΅ арифмСтичСскиС ΠΎΠΏΠ΅Ρ€Π°Ρ†ΠΈΠΈ Π½Π΅ ΡΠ²Π»ΡΡŽΡ‚ΡΡ Π°Ρ‚ΠΎΠΌΠ°Ρ€Π½Ρ‹ΠΌΠΈ. ΠŸΠΎΡΡ‚ΠΎΠΌΡƒ Π² пространствС ΠΈΠΌΠ΅Π½ System.Threading прСдлагаСтся Ρ‚ΠΈΠΏ, ΠΏΠΎΠ·Π²ΠΎΠ»ΡΡŽΡ‰ΠΈΠΉ Π²ΠΎΠ·Π΄Π΅ΠΉΡΡ‚Π²ΠΎΠ²Π°Ρ‚ΡŒ Π½Π° ΠΎΡ‚Π΄Π΅Π»ΡŒΠ½Ρ‹ΠΉ элСмСнт Π΄Π°Π½Π½Ρ‹Ρ… Π°Ρ‚ΠΎΠΌΠ°Ρ€Π½ΠΎ с мСньшСй Π½Π°Π³Ρ€ΡƒΠ·ΠΊΠΎΠΉ, Ρ‡Π΅ΠΌ это Π΄Π΅Π»Π°Π΅Ρ‚ Ρ‚ΠΈΠΏ Monitor. Π’ΠΈΠΏ класса Interlocked опрСдСляСт статичСскиС Ρ‡Π»Π΅Π½Ρ‹, описания ΠΊΠΎΡ‚ΠΎΡ€Ρ‹Ρ… ΠΏΡ€ΠΈΠ²Π΅Π΄Π΅Π½Ρ‹ Π² Ρ‚Π°Π±Π». 14.4.

Π’Π°Π±Π»ΠΈΡ†Π° 14.4. Π§Π»Π΅Π½Ρ‹ Ρ‚ΠΈΠΏΠ° System.Threading.Interlocked

Π§Π»Π΅Π½ ОписаниС CompareExchange() БСзопасно провСряСт Π΄Π²Π° значСния Π½Π° равСнство, ΠΈ Ссли ΠΎΠ½ΠΈ Ρ€Π°Π²Π½Ρ‹, замСняСт ΠΎΠ΄Π½ΠΎ ΠΈΠ· Π·Π½Π°Ρ‡Π΅Π½ΠΈΠΉ Ρ‚Ρ€Π΅Ρ‚ΡŒΠΈΠΌ Decrement() БСзопасно ΡƒΠΌΠ΅Π½ΡŒΡˆΠ°Π΅Ρ‚ Π·Π½Π°Ρ‡Π΅Π½ΠΈΠ΅ Π½Π° 1 Exchange() БСзопасно мСняСт Π΄Π²Π° значСния мСстами Increment() БСзопасно выполняСт ΠΏΡ€ΠΈΡ€Π°Ρ‰Π΅Π½ΠΈΠ΅ значСния Π½Π° 1

Π₯отя это ΠΌΠΎΠΆΠ΅Ρ‚ ΠΈ Π½Π΅ ΠΊΠ°Π·Π°Ρ‚ΡŒΡΡ ΠΎΡ‡Π΅Π²ΠΈΠ΄Π½Ρ‹ΠΌ Π½Π° ΠΏΠ΅Ρ€Π²Ρ‹ΠΉ взгляд, процСсс Π°Ρ‚ΠΎΠΌΠ°Ρ€Π½ΠΎΠ³ΠΎ измСнСния ΠΎΠ΄Π½ΠΎΠ³ΠΎ значСния являСтся Π²ΠΏΠΎΠ»Π½Π΅ Ρ‚ΠΈΠΏΠΈΡ‡Π½Ρ‹ΠΌ Π² ΠΌΠ½ΠΎΠ³ΠΎΠΏΠΎΡ‚ΠΎΡ‡Π½ΠΎΠΌ ΠΎΠΊΡ€ΡƒΠΆΠ΅Π½ΠΈΠΈ. ΠŸΡ€Π΅Π΄ΠΏΠΎΠ»ΠΎΠΆΠΈΠΌ, Ρ‡Ρ‚ΠΎ Ρƒ нас Π΅ΡΡ‚ΡŒ ΠΌΠ΅Ρ‚ΠΎΠ΄ AddOne(), ΠΊΠΎΡ‚ΠΎΡ€Ρ‹ΠΉ ΡƒΠ²Π΅Π»ΠΈΡ‡ΠΈΠ²Π°Π΅Ρ‚ Ρ†Π΅Π»ΠΎΡ‡ΠΈΡΠ»Π΅Π½Π½ΡƒΡŽ ΠΏΠ΅Ρ€Π΅ΠΌΠ΅Π½Π½ΡƒΡŽ intVal Π½Π° Π΅Π΄ΠΈΠ½ΠΈΡ†Ρƒ. ВмСсто ΠΏΡ€ΠΎΠ³Ρ€Π°ΠΌΠΌΠ½ΠΎΠ³ΠΎ ΠΊΠΎΠ΄Π° синхронизации, ΠΏΠΎΠ΄ΠΎΠ±Π½ΠΎΠ³ΠΎ ΡΠ»Π΅Π΄ΡƒΡŽΡ‰Π΅ΠΌΡƒ;

public void AddOne() {

 lock(this) {

  intVal++;

 }

}

ΠΌΠΎΠΆΠ½ΠΎ ΠΏΡ€Π΅Π΄Π»ΠΎΠΆΠΈΡ‚ΡŒ Π±ΠΎΠ»Π΅Π΅ простой ΠΏΡ€ΠΎΠ³Ρ€Π°ΠΌΠΌΠ½Ρ‹ΠΉ ΠΊΠΎΠ΄, Π² ΠΊΠΎΡ‚ΠΎΡ€ΠΎΠΌ ΠΈΡΠΏΠΎΠ»ΡŒΠ·ΡƒΠ΅Ρ‚ΡΡ статичСский ΠΌΠ΅Ρ‚ΠΎΠ΄ Interlocked.Increment(). ΠŸΡ€ΠΎΡΡ‚ΠΎ ΠΏΠ΅Ρ€Π΅Π΄Π°ΠΉΡ‚Π΅ ΠΏΠ΅Ρ€Π΅ΠΌΠ΅Π½Π½ΡƒΡŽ для приращСния ΠΏΠΎ ссылкС. ΠžΠ±Ρ€Π°Ρ‚ΠΈΡ‚Π΅ Π²Π½ΠΈΠΌΠ°Π½ΠΈΠ΅ Π½Π° Ρ‚ΠΎ, Ρ‡Ρ‚ΠΎ ΠΌΠ΅Ρ‚ΠΎΠ΄ Increment() Π½Π΅ Ρ‚ΠΎΠ»ΡŒΠΊΠΎ измСняСт Π·Π½Π°Ρ‡Π΅Π½ΠΈΠ΅ ΠΏΠΎΡΡ‚ΡƒΠΏΠ°ΡŽΡ‰Π΅Π³ΠΎ ΠΏΠ°Ρ€Π°ΠΌΠ΅Ρ‚Ρ€Π°, Π½ΠΎ ΠΈ Π²ΠΎΠ·Π²Ρ€Π°Ρ‰Π°Π΅Ρ‚ Π½ΠΎΠ²ΠΎΠ΅ Π·Π½Π°Ρ‡Π΅Π½ΠΈΠ΅.

public void AddOne() {

 int newVal = Interlocked.Increment(ref intVal);

}

Π’ Π΄ΠΎΠΏΠΎΠ»Π½Π΅Π½ΠΈΠ΅ ΠΊ Increment() ΠΈ Decrement() Ρ‚ΠΈΠΏ Interlocked позволяСт Π°Ρ‚ΠΎΠΌΠ°Ρ€Π½ΠΎ ΠΏΡ€ΠΈΡΠ²Π°ΠΈΠ²Π°Ρ‚ΡŒ числовыС ΠΈ ΠΎΠ±ΡŠΠ΅ΠΊΡ‚Π½Ρ‹Π΅ Π΄Π°Π½Π½Ρ‹Π΅. НапримСр, Ссли Π²Ρ‹ Ρ…ΠΎΡ‚ΠΈΡ‚Π΅ ΠΏΡ€ΠΈΡΠ²ΠΎΠΈΡ‚ΡŒ Ρ‡Π»Π΅Π½Ρƒ-ΠΏΠ΅Ρ€Π΅ΠΌΠ΅Π½Π½ΠΎΠΉ Π·Π½Π°Ρ‡Π΅Π½ΠΈΠ΅ 83, Π²Ρ‹ ΠΌΠΎΠΆΠ΅Ρ‚Π΅ ΠΈΠ·Π±Π΅ΠΆΠ°Ρ‚ΡŒ нСобходимости явного использования ΠΎΠΏΠ΅Ρ€Π°Ρ‚ΠΎΡ€Π° lock (ΠΈΠ»ΠΈ явного примСнСния Π»ΠΎΠ³ΠΈΠΊΠΈ Monitor), Ссли ΠΈΡΠΏΠΎΠ»ΡŒΠ·ΡƒΠ΅Ρ‚Π΅ ΠΌΠ΅Ρ‚ΠΎΠ΄ Interlocked.Exchange().

public void SafeAssignment() {

 Interlocked.Exchange(ref myInt, 83);

}

НаконСц, ΠΏΡ€ΠΈ ΠΏΡ€ΠΎΠ²Π΅Ρ€ΠΊΠ΅ Π΄Π²ΡƒΡ… Π·Π½Π°Ρ‡Π΅Π½ΠΈΠΉ Π½Π° равСнство, Ρ‡Ρ‚ΠΎΠ±Ρ‹ ΠΎΠ±Π΅ΡΠΏΠ΅Ρ‡ΠΈΡ‚ΡŒ ΠΏΠΎΡ‚ΠΎΠΊΠΎΠ²ΡƒΡŽ Π±Π΅Π·ΠΎΠΏΠ°ΡΠ½ΠΎΡΡ‚ΡŒ элСмСнту сравнСния, ΠΌΠΎΠΆΠ΅Ρ‚Π΅ ΠΈΡΠΏΠΎΠ»ΡŒΠ·ΠΎΠ²Π°Ρ‚ΡŒ ΠΌΠ΅Ρ‚ΠΎΠ΄ Interlocked.CompareExchange(), ΠΊΠ°ΠΊ ΠΏΠΎΠΊΠ°Π·Π°Π½ΠΎ Π½ΠΈΠΆΠ΅.

public void CompareAndExchange() {

 // Если Π·Π½Π°Ρ‡Π΅Π½ΠΈΠ΅ΠΌ i являСтся 83, ΠΈΠ·ΠΌΠ΅Π½ΠΈΡ‚ΡŒ Π΅Π³ΠΎ Π½Π° 99.

 Interlocked.CompareExchange(ref i, 99, 83);

}

Бинхронизация с ΠΏΠΎΠΌΠΎΡ‰ΡŒΡŽ Π°Ρ‚Ρ€ΠΈΠ±ΡƒΡ‚Π° [Synchronization]

ПослСдним ΠΈΠ· рассмотрСнных здСсь ΠΏΡ€ΠΈΠΌΠΈΡ‚ΠΈΠ²ΠΎΠ² синхронизации Π±ΡƒΠ΄Π΅Ρ‚ Π°Ρ‚Ρ€ΠΈΠ±ΡƒΡ‚ [Synchronization], ΠΊΠΎΡ‚ΠΎΡ€Ρ‹ΠΉ опрСдСляСтся Π² пространствС ΠΈΠΌΠ΅Π½ System.Runtime.Remoting.Contexts. Π­Ρ‚ΠΎΡ‚ Π°Ρ‚Ρ€ΠΈΠ±ΡƒΡ‚ уровня класса для бСзопасности ΠΏΠΎΡ‚ΠΎΠΊΠ° эффСктивно Π±Π»ΠΎΠΊΠΈΡ€ΡƒΠ΅Ρ‚ вСсь ΠΏΡ€ΠΎΠ³Ρ€Π°ΠΌΠΌΠ½Ρ‹ΠΉ ΠΊΠΎΠ΄ Ρ‡Π»Π΅Π½ΠΎΠ² экзСмпляра. Когда срСда CLR Ρ€Π°Π·ΠΌΠ΅Ρ‰Π°Π΅Ρ‚ ΠΎΠ±ΡŠΠ΅ΠΊΡ‚, ΠΈΠΌΠ΅ΡŽΡ‰ΠΈΠΉ Π°Ρ‚Ρ€ΠΈΠ±ΡƒΡ‚ [Synchronization], ΠΎΠ½Π° ΠΏΠΎΠΌΠ΅Ρ‰Π°Π΅Ρ‚ этот ΠΎΠ±ΡŠΠ΅ΠΊΡ‚ Π² Ρ€Π°ΠΌΠΊΠΈ синхронизированного контСкста. Π’Ρ‹ Π΄ΠΎΠ»ΠΆΠ½Ρ‹ ΠΏΠΎΠΌΠ½ΠΈΡ‚ΡŒ ΠΈΠ· Π³Π»Π°Π²Ρ‹ 13, Ρ‡Ρ‚ΠΎ ΠΎΠ±ΡŠΠ΅ΠΊΡ‚Ρ‹, ΠΊΠΎΡ‚ΠΎΡ€Ρ‹Π΅ Π½Π΅ Π΄ΠΎΠ»ΠΆΠ½Ρ‹ ΠΏΠΎΠΊΠΈΠ΄Π°Ρ‚ΡŒ контСкстныС Π³Ρ€Π°Π½ΠΈΡ†Ρ‹, ΡΠ²Π»ΡΡŽΡ‚ΡΡ ΠΏΡ€ΠΎΠΈΠ·Π²ΠΎΠ΄Π½Ρ‹ΠΌΠΈ ΠΎΡ‚ ContextBoundObject. ΠŸΠΎΡΡ‚ΠΎΠΌΡƒ, Ρ‡Ρ‚ΠΎΠ±Ρ‹ ΡΠ΄Π΅Π»Π°Ρ‚ΡŒ Ρ‚ΠΈΠΏ класса Printer устойчивым Π² ΠΎΡ‚Π½ΠΎΡˆΠ΅Π½ΠΈΠΈ ΠΏΠΎΡ‚ΠΎΠΊΠΎΠ² (Π±Π΅Π· добавлСния ΠΏΡ€ΠΎΠ³Ρ€Π°ΠΌΠΌΠ½ΠΎΠ³ΠΎ ΠΊΠΎΠ΄Π° Π·Π°Ρ‰ΠΈΡ‚Ρ‹ ΠΏΠΎΡ‚ΠΎΠΊΠΎΠ² Π²Ρ€ΡƒΡ‡Π½ΡƒΡŽ), слСдуСт ΠΈΠ·ΠΌΠ΅Π½ΠΈΡ‚ΡŒ ΡΠΎΠΎΡ‚Π²Π΅Ρ‚ΡΡ‚Π²ΡƒΡŽΡ‰Π΅Π΅ ΠΎΠΏΡ€Π΅Π΄Π΅Π»Π΅Π½ΠΈΠ΅ Ρ‚Π°ΠΊ.

using System.Runtime.Remoting.Contexts;

...

// ВсС ΠΌΠ΅Ρ‚ΠΎΠ΄Ρ‹ Printer Ρ‚Π΅ΠΏΠ΅Ρ€ΡŒ потокоустойчивы!

[Synchronization]

public class Printer: Π‘ontextBoundObject {

 public void PrintNumbers() {

 β€¦

 }

}

Π­Ρ‚ΠΎΡ‚ ΠΏΠΎΠ΄Ρ…ΠΎΠ΄ ΠΌΠΎΠΆΠ½ΠΎ Π½Π°Π·Π²Π°Ρ‚ΡŒ способом создания потокоустойчивого ΠΏΡ€ΠΎΠ³Ρ€Π°ΠΌΠΌΠ½ΠΎΠ³ΠΎ ΠΊΠΎΠ΄Π° для Π»Π΅Π½ΠΈΠ²Ρ‹Ρ…, ΠΏΠΎΡΠΊΠΎΠ»ΡŒΠΊΡƒ здСсь Π½Π΅ трСбуСтся Π²Ρ‹ΡΡΠ½ΡΡ‚ΡŒ, ΠΊΠ°ΠΊΠΈΠ΅ Ρ„Ρ€Π°Π³ΠΌΠ΅Π½Ρ‚Ρ‹ Ρ‚ΠΈΠΏΠ° ΠΌΠΎΠ³ΡƒΡ‚ ΠΈΡΠΏΡ‹Ρ‚Ρ‹Π²Π°Ρ‚ΡŒ влияниС Π²Π½Π΅ΡˆΠ½ΠΈΡ… ΠΏΠΎΡ‚ΠΎΠΊΠΎΠ². Π“Π»Π°Π²Π½Ρ‹ΠΌ нСдостатком этого ΠΏΠΎΠ΄Ρ…ΠΎΠ΄Π° являСтся Ρ‚ΠΎ, Ρ‡Ρ‚ΠΎ Π΄Π°ΠΆΠ΅ Ссли ΠΊΠ°ΠΊΠΎΠΉ-Ρ‚ΠΎ ΠΌΠ΅Ρ‚ΠΎΠ΄ ΠΈ Π½Π΅ испытываСт влияния Π²Π½Π΅ΡˆΠ½ΠΈΡ… ΠΏΠΎΡ‚ΠΎΠΊΠΎΠ², срСда CLR всС Ρ€Π°Π²Π½ΠΎ Π±Π»ΠΎΠΊΠΈΡ€ΡƒΠ΅Ρ‚ ΠΎΠ±Ρ€Π°Ρ‰Π΅Π½ΠΈΠ΅ ΠΊ этому ΠΌΠ΅Ρ‚ΠΎΠ΄Ρƒ. ΠžΡ‡Π΅Π²ΠΈΠ΄Π½ΠΎ, это ΠΌΠΎΠΆΠ΅Ρ‚ ΡƒΡ…ΡƒΠ΄ΡˆΠΈΡ‚ΡŒ ΠΎΠ±Ρ‰ΠΈΠ΅ характСристики функционирования Ρ‚ΠΈΠΏΠ°, Ρ‚Π°ΠΊ Ρ‡Ρ‚ΠΎ ΠΈΡΠΏΠΎΠ»ΡŒΠ·ΡƒΠΉΡ‚Π΅ ΡƒΠΊΠ°Π·Π°Π½Π½Ρ‹ΠΉ ΠΏΠΎΠ΄Ρ…ΠΎΠ΄ с ΠΎΡΡ‚ΠΎΡ€ΠΎΠΆΠ½ΠΎΡΡ‚ΡŒΡŽ.

Π˜Ρ‚Π°ΠΊ, ΠΌΡ‹ с Π²Π°ΠΌΠΈ обсудили Ρ†Π΅Π»Ρ‹ΠΉ ряд ΠΏΠΎΠ΄Ρ…ΠΎΠ΄ΠΎΠ² ΠΊ Ρ€Π΅ΡˆΠ΅Π½ΠΈΡŽ вопроса синхронизированного доступа ΠΊ ΠΎΠ±Ρ‰ΠΈΠΌ Π±Π»ΠΎΠΊΠ°ΠΌ Π΄Π°Π½Π½Ρ‹Ρ…. Π‘ΡƒΠ΄ΡŒΡ‚Π΅ ΡƒΠ²Π΅Ρ€Π΅Π½Ρ‹, Π² пространствС ΠΈΠΌΠ΅Π½ System.Threading Π΅ΡΡ‚ΡŒ ΠΈ Π΄Ρ€ΡƒΠ³ΠΈΠ΅ Ρ‚ΠΈΠΏΡ‹, ΠΊΠΎΡ‚ΠΎΡ€Ρ‹Π΅ я Π½Π°ΡΡ‚ΠΎΡΡ‚Π΅Π»ΡŒΠ½ΠΎ Ρ€Π΅ΠΊΠΎΠΌΠ΅Π½Π΄ΡƒΡŽ Π²Π°ΠΌ постСпСнно ΠΈΡΡΠ»Π΅Π΄ΠΎΠ²Π°Ρ‚ΡŒ. Π’ Π·Π°Π²Π΅Ρ€ΡˆΠ΅Π½ΠΈΠ΅ этой Π³Π»Π°Π²Ρ‹, посвящСнной ΠΏΡ€ΠΎΠ³Ρ€Π°ΠΌΠΌΠΈΡ€ΠΎΠ²Π°Π½ΠΈΡŽ ΠΏΠΎΡ‚ΠΎΠΊΠΎΠ², Π΄Π°Π²Π°ΠΉΡ‚Π΅ рассмотрим Ρ‚Ρ€ΠΈ: Π΄ΠΎΠΏΠΎΠ»Π½ΠΈΡ‚Π΅Π»ΡŒΠ½Ρ‹Ρ… Ρ‚ΠΈΠΏΠ°: TimerCallback, Timer ΠΈ ThreadPool.

ΠŸΡ€ΠΎΠ³Ρ€Π°ΠΌΠΌΠΈΡ€ΠΎΠ²Π°Π½ΠΈΠ΅ с ΠΏΠΎΠΌΠΎΡ‰ΡŒΡŽ Ρ‚Π°ΠΉΠΌΠ΅Ρ€ΠΎΠ² ΠΎΠ±Ρ€Π°Ρ‚Π½ΠΎΠ³ΠΎ Π²Ρ‹Π·ΠΎΠ²Π°

Π’ΠΎ ΠΌΠ½ΠΎΠ³ΠΈΡ… прилоТСниях Π²ΠΎΠ·Π½ΠΈΠΊΠ°Π΅Ρ‚ Π½Π΅ΠΎΠ±Ρ…ΠΎΠ΄ΠΈΠΌΠΎΡΡ‚ΡŒ Π²Ρ‹Π·Ρ‹Π²Π°Ρ‚ΡŒ ΠΊΠΎΠ½ΠΊΡ€Π΅Ρ‚Π½Ρ‹ΠΉ ΠΌΠ΅Ρ‚ΠΎΠ΄ Ρ‡Π΅Ρ€Π΅Π· рСгулярныС ΠΏΡ€ΠΎΠΌΠ΅ΠΆΡƒΡ‚ΠΊΠΈ Π²Ρ€Π΅ΠΌΠ΅Π½ΠΈ. НапримСр, Π² ΠΎΠ΄Π½ΠΎΠΌ ΠΏΡ€ΠΈΠ»ΠΎΠΆΠ΅Π½ΠΈΠΈ ΠΌΠΎΠΆΠ΅Ρ‚ ΠΏΠΎΡ‚Ρ€Π΅Π±ΠΎΠ²Π°Ρ‚ΡŒΡΡ ΠΎΡ‚ΠΎΠ±Ρ€Π°ΠΆΠ΅Π½ΠΈΠ΅ Ρ‚Π΅ΠΊΡƒΡ‰Π΅Π³ΠΎ Π²Ρ€Π΅ΠΌΠ΅Π½ΠΈ Π² строкС состояния с ΠΏΠΎΠΌΠΎΡ‰ΡŒΡŽ Π½Π΅ΠΊΠΎΡ‚ΠΎΡ€ΠΎΠΉ Π²ΡΠΏΠΎΠΌΠΎΠ³Π°Ρ‚Π΅Π»ΡŒΠ½ΠΎΠΉ Ρ„ΡƒΠ½ΠΊΡ†ΠΈΠΈ. Π’ Π΄Ρ€ΡƒΠ³ΠΎΠΌ ΠΏΡ€ΠΈΠ»ΠΎΠΆΠ΅Π½ΠΈΠΈ ΠΌΠΎΠΆΠ΅Ρ‚ ΠΏΠΎΠ½Π°Π΄ΠΎΠ±ΠΈΡ‚ΡŒΡΡ пСриодичСский Π²Ρ‹Π·ΠΎΠ² Π²ΡΠΏΠΎΠΌΠΎΠ³Π°Ρ‚Π΅Π»ΡŒΠ½ΠΎΠΉ Ρ„ΡƒΠ½ΠΊΡ†ΠΈΠΈ, Π²Ρ‹ΠΏΠΎΠ»Π½ΡΡŽΡ‰Π΅ΠΉ Π² Ρ„ΠΎΠ½ΠΎΠ²ΠΎΠΌ Ρ€Π΅ΠΆΠΈΠΌΠ΅ ΠΊΠ°ΠΊΠΈΠ΅-Ρ‚ΠΎ нСкритичСскиС Π·Π°Π΄Π°Ρ‡ΠΈ, Π½Π°ΠΏΡ€ΠΈΠΌΠ΅Ρ€ ΠΏΡ€ΠΎΠ²Π΅Ρ€ΠΊΡƒ поступлСния Π½ΠΎΠ²Ρ‹Ρ… сообщСний элСктронной ΠΏΠΎΡ‡Ρ‚Ρ‹. Для Ρ‚Π°ΠΊΠΈΡ… ситуаций ΠΌΠΎΠΆΠ½ΠΎ ΠΈΡΠΏΠΎΠ»ΡŒΠ·ΠΎΠ²Π°Ρ‚ΡŒ Ρ‚ΠΈΠΏ System. Threading.Timer Π² совокупности с ΡΠΎΠΎΡ‚Π²Π΅Ρ‚ΡΡ‚Π²ΡƒΡŽΡ‰ΠΈΠΌ Π΄Π΅Π»Π΅Π³Π°Ρ‚ΠΎΠΌ TimerCallback.

Для ΠΏΡ€ΠΈΠΌΠ΅Ρ€Π° ΠΏΡ€Π΅Π΄ΠΏΠΎΠ»ΠΎΠΆΠΈΠΌ, Ρ‡Ρ‚ΠΎ Π½Π°ΠΌ Π½ΡƒΠΆΠ½ΠΎ ΡΠΎΠ·Π΄Π°Ρ‚ΡŒ консольноС ΠΏΡ€ΠΈΠ»ΠΎΠΆΠ΅Π½ΠΈΠ΅, ΠΊΠΎΡ‚ΠΎΡ€ΠΎΠ΅ СТСсСкундно Π²Ρ‹Π²ΠΎΠ΄ΠΈΡ‚ Ρ‚Π΅ΠΊΡƒΡ‰Π΅Π΅ врСмя, ΠΏΠΎΠΊΠ° ΠΏΠΎΠ»ΡŒΠ·ΠΎΠ²Π°Ρ‚Π΅Π»ΡŒ Π½Π΅ Π½Π°ΠΆΠΌΠ΅Ρ‚ ΠΊΠ»Π°Π²ΠΈΡˆΡƒ, Π·Π°Π²Π΅Ρ€ΡˆΠ°ΡŽΡ‰ΡƒΡŽ Π²Ρ‹ΠΏΠΎΠ»Π½Π΅Π½ΠΈΠ΅ этого прилоТСния. ΠŸΠ΅Ρ€Π²Ρ‹ΠΌ ΠΎΡ‡Π΅Π²ΠΈΠ΄Π½Ρ‹ΠΌ шагом здСсь являСтся созданиС ΠΌΠ΅Ρ‚ΠΎΠ΄Π°, ΠΊΠΎΡ‚ΠΎΡ€Ρ‹ΠΉ Π±ΡƒΠ΄Π΅Ρ‚ Π²Ρ‹Π·Ρ‹Π²Π°Ρ‚ΡŒΡΡ Ρ‚ΠΈΠΏΠΎΠΌ Timer.

class TimePrinter {

 static void PrintTime(object state) {

  Console.WriteLine("ВрСмя: {0}", DateTime.Now.ToLongTimeString());

 }

}

Π­Ρ‚ΠΎΡ‚ ΠΌΠ΅Ρ‚ΠΎΠ΄ ΠΈΠΌΠ΅Π΅Ρ‚ ΠΎΠ΄ΠΈΠ½ ΠΏΠ°Ρ€Π°ΠΌΠ΅Ρ‚Ρ€ Ρ‚ΠΈΠΏΠ° System.Object ΠΈ Π²ΠΎΠ·Π²Ρ€Π°Ρ‰Π°Π΅Ρ‚ void. Вакая структура ΠΌΠ΅Ρ‚ΠΎΠ΄Π° ΠΎΠ±ΡΠ·Π°Ρ‚Π΅Π»ΡŒΠ½Π°, ΠΏΠΎΡΠΊΠΎΠ»ΡŒΠΊΡƒ Π΄Π΅Π»Π΅Π³Π°Ρ‚ TimerCallback ΠΌΠΎΠΆΠ΅Ρ‚ Π²Ρ‹Π·Ρ‹Π²Π°Ρ‚ΡŒ Ρ‚ΠΎΠ»ΡŒΠΊΠΎ Ρ‚Π°ΠΊΠΈΠ΅ ΠΌΠ΅Ρ‚ΠΎΠ΄Ρ‹. Π—Π½Π°Ρ‡Π΅Π½ΠΈΠ΅, ΠΏΠ΅Ρ€Π΅Π΄Π°Π²Π°Π΅ΠΌΠΎΠ΅ Ρ†Π΅Π»Π΅Π²ΠΎΠΌΡƒ ΠΌΠ΅Ρ‚ΠΎΠ΄Ρƒ Π΄Π΅Π»Π΅Π³Π°Ρ‚Π° TimerCallback, ΠΌΠΎΠΆΠ΅Ρ‚ ΠΏΡ€Π΅Π΄ΡΡ‚Π°Π²Π»ΡΡ‚ΡŒ Π»ΡŽΠ±ΡƒΡŽ ΠΈΠ½Ρ„ΠΎΡ€ΠΌΠ°Ρ†ΠΈΡŽ (Ρ‚Π°ΠΊ, Π² случаС элСктронной ΠΏΠΎΡ‡Ρ‚Ρ‹ это ΠΌΠΎΠΆΠ΅Ρ‚ Π±Ρ‹Ρ‚ΡŒ имя сСрвСра Microsoft Exchange, с ΠΊΠΎΡ‚ΠΎΡ€Ρ‹ΠΌ трСбуСтся взаимодСйствиС Π² Ρ…ΠΎΠ΄Π΅ процСсса). А Ρ‚Π°ΠΊ ΠΊΠ°ΠΊ ΠΏΠ°Ρ€Π°ΠΌΠ΅Ρ‚Ρ€ являСтся Ρ‚ΠΈΠΏΠΎΠΌ System.Object, Π² Π΄Π΅ΠΉΡΡ‚Π²ΠΈΡ‚Π΅Π»ΡŒΠ½ΠΎΡΡ‚ΠΈ ΠΌΠΎΠΆΠ½ΠΎ ΠΏΠ΅Ρ€Π΅Π΄Π°Ρ‚ΡŒ любоС число Π°Ρ€Π³ΡƒΠΌΠ΅Π½Ρ‚ΠΎΠ², Ссли ΠΈΡΠΏΠΎΠ»ΡŒΠ·ΠΎΠ²Π°Ρ‚ΡŒ System.Array ΠΈΠ»ΠΈ ΠΏΠΎΠ»ΡŒΠ·ΠΎΠ²Π°Ρ‚Π΅Π»ΡŒΡΠΊΠΈΠΉ класс (структуру).