线程安全 一
using System;
using System.Threading;
using System.Runtime.Remoting.Contexts;
using System.Runtime.CompilerServices;
// Note that the instance variable count is shared between the two methods Read
// and Increment. Threads concurrently executing one or both of these methods can
// interfere with each other unless action is taken to synchronize access
class CounterUnsafe
{
int count = 0;
public void Increment()
{
// following code is not thread-safe and has a race condition
Console.WriteLine(
"Start Resource writing count: {0}", count);
// the following four lines simulate count++ with a very large
// window of time between count being read and being incremented.
// This large window ensures that the race condition will create
// errors often when the code is accessed concurrently by multiple threads.
int tempCount = count;
Thread.Sleep(50);
tempCount++;
count = tempCount;
Console.WriteLine(
"Stop Resource writing count: {0}", count);
}
}
// Context-bound type with the Synchronization context attribute.
[Synchronization()]
class CounterSynchronizedContext : ContextBoundObject
{
static int staticCount = 0;
int instanceCount = 0;
public void IncrementInstance()
{
Console.WriteLine(
"Start Object:{0} Thread:{1} Resource writing count, instance:{2}",
this.GetHashCode(), Thread.CurrentThread.GetHashCode(),
instanceCount);
int tempStaticCount = staticCount;
int tempInstanceCount = instanceCount;
Thread.Sleep(50);
tempInstanceCount++;
instanceCount = tempInstanceCount;
Console.WriteLine(
"Stop Object:{0} Thread:{1} Resource writing count, instance:{2}",
this.GetHashCode(), Thread.CurrentThread.GetHashCode(),
instanceCount);
}
public static void IncrementStatic()
{
Console.WriteLine(
"Start Thread:{0} Resource writing count, static:{1}",
Thread.CurrentThread.GetHashCode(),
staticCount);
int tempStaticCount = staticCount;
Thread.Sleep(50);
tempStaticCount++;
staticCount = tempStaticCount;
Console.WriteLine(
"Stop Thread:{0} Resource writing count, static:{1}",
Thread.CurrentThread.GetHashCode(),
staticCount);
}
}
class CounterSynchronizedCodeRegion
{
static int staticCount = 0;
int instanceCount = 0;
[MethodImplAttribute(MethodImplOptions.Synchronized)]
public void IncrementInstance()
{
Console.WriteLine(
"Start Object:{0} Thread:{1} Resource writing count, instance:{2}",
this.GetHashCode(), Thread.CurrentThread.GetHashCode(),
instanceCount);
int tempInstanceCount = instanceCount;
Thread.Sleep(50);
tempInstanceCount++;
instanceCount = tempInstanceCount;
Console.WriteLine(
"Stop Object:{0} Thread:{1} Resource writing count, instance:{2}",
this.GetHashCode(), Thread.CurrentThread.GetHashCode(),
instanceCount);
}
[MethodImplAttribute(MethodImplOptions.Synchronized)]
public static void IncrementStatic()
{
Console.WriteLine(
"Start Thread:{0} Resource writing count, static:{1}",
Thread.CurrentThread.GetHashCode(),
staticCount);
int tempStaticCount = staticCount;
Thread.Sleep(50);
tempStaticCount++;
staticCount = tempStaticCount;
Console.WriteLine(
"Stop Thread:{0} Resource writing count, static:{1}",
Thread.CurrentThread.GetHashCode(),
staticCount);
}
}
class App
{
public static void Main()
{
Thread t1, t2, t3;
Console.WriteLine("\n\nStarting Unsafe Test");
CounterUnsafe counterUnsafe = new CounterUnsafe();
t1 = new
Thread( new
ThreadStart(counterUnsafe.Increment));
t1.Start();
t2 = new
Thread( new
ThreadStart(counterUnsafe.Increment));
t2.Start();
t3 = new
Thread( new
ThreadStart(counterUnsafe.Increment));
t3.Start();
// wait for all threads to indicate that they are done.
t1.Join();t2.Join();t3.Join();
Console.WriteLine("All Unsafe threads have completed.");
// Synchronized context doesn't prevent static methods from concurrently executing
Console.WriteLine("\n\nStarting Static Method Synchronized Context Test");
t1 = new
Thread( new
ThreadStart(CounterSynchronizedContext.IncrementStatic));
t1.Start();
t2 = new
Thread( new
ThreadStart(CounterSynchronizedContext.IncrementStatic));
t2.Start();
t3 = new
Thread( new
ThreadStart(CounterSynchronizedContext.IncrementStatic));
t3.Start();
// wait for all threads to indicate that they are done.
t1.Join();t2.Join();t3.Join();
Console.WriteLine("All Static Method Synchronized Context threads have completed.");
// Synchronized context does prevent instance methods from concurrently executing
Console.WriteLine("\n\nStarting Instance Method Synchronized Context Test");
CounterSynchronizedContext counterSynchronizedContext = new CounterSynchronizedContext();
t1 = new
Thread( new
ThreadStart(counterSynchronizedContext.IncrementInstance));
t1.Start();
t2 = new
Thread( new
ThreadStart(counterSynchronizedContext.IncrementInstance));
t2.Start();
t3 = new
Thread( new
ThreadStart(counterSynchronizedContext.IncrementInstance));
t3.Start();
// wait for all threads to indicate that they are done.
t1.Join();t2.Join();t3.Join();
Console.WriteLine("All Instance Method Synchronized Context threads have completed.");
Console.WriteLine("\n\nStarting Static Method Synchronized Code Region Test");
t1 = new
Thread( new
ThreadStart(CounterSynchronizedCodeRegion.IncrementStatic));
t1.Start();
t2 = new
Thread( new
ThreadStart(CounterSynchronizedCodeRegion.IncrementStatic));
t2.Start();
t3 = new
Thread( new
ThreadStart(CounterSynchronizedCodeRegion.IncrementStatic));
t3.Start();
// wait for all threads to indicate that they are done.
t1.Join();t2.Join();t3.Join();
Console.WriteLine("All Static Method Synchronized Code Region threads have completed.");
// Method Synchronization is similar to Monitor and prevents
// concurrent access to both static and instance methods
Console.WriteLine("\n\nStarting Instance Method Synchronized Code Region Test");
CounterSynchronizedCodeRegion counterSynchronizedCodeRegion = new CounterSynchronizedCodeRegion();
t1 = new
Thread( new
ThreadStart(counterSynchronizedCodeRegion.IncrementInstance));
t1.Start();
t2 = new
Thread( new
ThreadStart(counterSynchronizedCodeRegion.IncrementInstance));
t2.Start();
t3 = new
Thread( new
ThreadStart(counterSynchronizedCodeRegion.IncrementInstance));
t3.Start();
// wait for all threads to indicate that they are done.
t1.Join();t2.Join();t3.Join();
Console.WriteLine("All Static Method Synchronized Code Region threads have completed.");
}
}
using System.Threading;
using System.Runtime.Remoting.Contexts;
using System.Runtime.CompilerServices;
// Note that the instance variable count is shared between the two methods Read
// and Increment. Threads concurrently executing one or both of these methods can
// interfere with each other unless action is taken to synchronize access
class CounterUnsafe
{
int count = 0;
public void Increment()
{
// following code is not thread-safe and has a race condition
Console.WriteLine(
"Start Resource writing count: {0}", count);
// the following four lines simulate count++ with a very large
// window of time between count being read and being incremented.
// This large window ensures that the race condition will create
// errors often when the code is accessed concurrently by multiple threads.
int tempCount = count;
Thread.Sleep(50);
tempCount++;
count = tempCount;
Console.WriteLine(
"Stop Resource writing count: {0}", count);
}
}
// Context-bound type with the Synchronization context attribute.
[Synchronization()]
class CounterSynchronizedContext : ContextBoundObject
{
static int staticCount = 0;
int instanceCount = 0;
public void IncrementInstance()
{
Console.WriteLine(
"Start Object:{0} Thread:{1} Resource writing count, instance:{2}",
this.GetHashCode(), Thread.CurrentThread.GetHashCode(),
instanceCount);
int tempStaticCount = staticCount;
int tempInstanceCount = instanceCount;
Thread.Sleep(50);
tempInstanceCount++;
instanceCount = tempInstanceCount;
Console.WriteLine(
"Stop Object:{0} Thread:{1} Resource writing count, instance:{2}",
this.GetHashCode(), Thread.CurrentThread.GetHashCode(),
instanceCount);
}
public static void IncrementStatic()
{
Console.WriteLine(
"Start Thread:{0} Resource writing count, static:{1}",
Thread.CurrentThread.GetHashCode(),
staticCount);
int tempStaticCount = staticCount;
Thread.Sleep(50);
tempStaticCount++;
staticCount = tempStaticCount;
Console.WriteLine(
"Stop Thread:{0} Resource writing count, static:{1}",
Thread.CurrentThread.GetHashCode(),
staticCount);
}
}
class CounterSynchronizedCodeRegion
{
static int staticCount = 0;
int instanceCount = 0;
[MethodImplAttribute(MethodImplOptions.Synchronized)]
public void IncrementInstance()
{
Console.WriteLine(
"Start Object:{0} Thread:{1} Resource writing count, instance:{2}",
this.GetHashCode(), Thread.CurrentThread.GetHashCode(),
instanceCount);
int tempInstanceCount = instanceCount;
Thread.Sleep(50);
tempInstanceCount++;
instanceCount = tempInstanceCount;
Console.WriteLine(
"Stop Object:{0} Thread:{1} Resource writing count, instance:{2}",
this.GetHashCode(), Thread.CurrentThread.GetHashCode(),
instanceCount);
}
[MethodImplAttribute(MethodImplOptions.Synchronized)]
public static void IncrementStatic()
{
Console.WriteLine(
"Start Thread:{0} Resource writing count, static:{1}",
Thread.CurrentThread.GetHashCode(),
staticCount);
int tempStaticCount = staticCount;
Thread.Sleep(50);
tempStaticCount++;
staticCount = tempStaticCount;
Console.WriteLine(
"Stop Thread:{0} Resource writing count, static:{1}",
Thread.CurrentThread.GetHashCode(),
staticCount);
}
}
class App
{
public static void Main()
{
Thread t1, t2, t3;
Console.WriteLine("\n\nStarting Unsafe Test");
CounterUnsafe counterUnsafe = new CounterUnsafe();
t1 = new
Thread( new
ThreadStart(counterUnsafe.Increment));
t1.Start();
t2 = new
Thread( new
ThreadStart(counterUnsafe.Increment));
t2.Start();
t3 = new
Thread( new
ThreadStart(counterUnsafe.Increment));
t3.Start();
// wait for all threads to indicate that they are done.
t1.Join();t2.Join();t3.Join();
Console.WriteLine("All Unsafe threads have completed.");
// Synchronized context doesn't prevent static methods from concurrently executing
Console.WriteLine("\n\nStarting Static Method Synchronized Context Test");
t1 = new
Thread( new
ThreadStart(CounterSynchronizedContext.IncrementStatic));
t1.Start();
t2 = new
Thread( new
ThreadStart(CounterSynchronizedContext.IncrementStatic));
t2.Start();
t3 = new
Thread( new
ThreadStart(CounterSynchronizedContext.IncrementStatic));
t3.Start();
// wait for all threads to indicate that they are done.
t1.Join();t2.Join();t3.Join();
Console.WriteLine("All Static Method Synchronized Context threads have completed.");
// Synchronized context does prevent instance methods from concurrently executing
Console.WriteLine("\n\nStarting Instance Method Synchronized Context Test");
CounterSynchronizedContext counterSynchronizedContext = new CounterSynchronizedContext();
t1 = new
Thread( new
ThreadStart(counterSynchronizedContext.IncrementInstance));
t1.Start();
t2 = new
Thread( new
ThreadStart(counterSynchronizedContext.IncrementInstance));
t2.Start();
t3 = new
Thread( new
ThreadStart(counterSynchronizedContext.IncrementInstance));
t3.Start();
// wait for all threads to indicate that they are done.
t1.Join();t2.Join();t3.Join();
Console.WriteLine("All Instance Method Synchronized Context threads have completed.");
Console.WriteLine("\n\nStarting Static Method Synchronized Code Region Test");
t1 = new
Thread( new
ThreadStart(CounterSynchronizedCodeRegion.IncrementStatic));
t1.Start();
t2 = new
Thread( new
ThreadStart(CounterSynchronizedCodeRegion.IncrementStatic));
t2.Start();
t3 = new
Thread( new
ThreadStart(CounterSynchronizedCodeRegion.IncrementStatic));
t3.Start();
// wait for all threads to indicate that they are done.
t1.Join();t2.Join();t3.Join();
Console.WriteLine("All Static Method Synchronized Code Region threads have completed.");
// Method Synchronization is similar to Monitor and prevents
// concurrent access to both static and instance methods
Console.WriteLine("\n\nStarting Instance Method Synchronized Code Region Test");
CounterSynchronizedCodeRegion counterSynchronizedCodeRegion = new CounterSynchronizedCodeRegion();
t1 = new
Thread( new
ThreadStart(counterSynchronizedCodeRegion.IncrementInstance));
t1.Start();
t2 = new
Thread( new
ThreadStart(counterSynchronizedCodeRegion.IncrementInstance));
t2.Start();
t3 = new
Thread( new
ThreadStart(counterSynchronizedCodeRegion.IncrementInstance));
t3.Start();
// wait for all threads to indicate that they are done.
t1.Join();t2.Join();t3.Join();
Console.WriteLine("All Static Method Synchronized Code Region threads have completed.");
}
}