2017-11-28 7 views
2

따르면 클래스 article 다음 스레드로부터 안전하지 않습니다를 만듭니다SynchronizationAttribute.SUPPORTED 동기화 내용

[Synchronization] 
public class Deadlock : ContextBoundObject 
{ 
    public DeadLock Other; 
    public void Demo() { Thread.Sleep (1000); Other.Hello(); } 
    void Hello()  { Console.WriteLine ("hello");  } 
} 

public class Test 
{ 
    static void Main() 
    { 
    Deadlock dead1 = new Deadlock(); 
    Deadlock dead2 = new Deadlock(); 
    dead1.Other = dead2; 
    dead2.Other = dead1; 
    new Thread (dead1.Demo).Start(); 
    dead2.Demo(); 
    } 
} 
그것은 않습니다

과 :

나의 이해에 따라 동안 잠금에 들어간 코드가 서로 다른 동기화 내용이 그것은 괜찮습니다. 하지만 설정하여 동기화 속성으로 플레이하기로 결정

[Synchronization(SynchronizationAttribute.SUPPORTED)] 

SUPPORTED 의미 :

가 다른 동기화 객체에서 인스턴스화 경우 기존의 동기화 컨텍스트를 조인, 그렇지 않으면 동기화 남아

이후 콘솔 응용 프로그램에 동기화 내용이 없습니다. 두 객체 모두 동기화 객체가없고 교착 상태에 빠지지 않아야합니다. 그러나 나는 여전히 교착 상태에 처해있다. 왜?

또한 [Synchronization] 속성을 제거했습니다. 여전히 교착 상태입니다. 어떤 영향을 받아 [Synchronization] 속성이 거부됩니까?

+0

당신이? ... 당신은 내가이 문제를 재현 할 수없는 순환 종속성 –

+0

를 만드는 것을 얻고있다 ... 오랫동안 코드를 실행하면 곧 stackoverlfow 예외를 얻을 것이다. SUPPORTED와'[Synchronization]이 없다면 교착 상태가 없다. – Evk

+0

시간 초과가 너무 길기 때문에 오버플로가 발생하지 않습니다. 그러나 아이디어를 얻었고 대답을 받아 들일 준비가되었습니다. – vico

답변

1

여기에 스레드 간 순환 종속성이 생겨서 스택 오버 플로우 예외가 발생할 수 있습니다. 여기에서 예외를 포착하지 않으면 보지 못할 수도 있습니다. 나는 당신에게 UnObservedExcpetion 핸들러를 사용하여 excpetion을 주거나 동일한 기능으로 exc35ion을 처리하려고 시도하는 것이 좋습니다. try, catch 블록을 넣으십시오.

이러한 상황을 피하려면 AutoResetEvent을 사용하는 것이 좋습니다. 아래는 동일한 코드 예제입니다.

public class MyThreadTest 
{ 
    static readonly AutoResetEvent thread1Step = new AutoResetEvent(false); 
    static readonly AutoResetEvent thread2Step = new AutoResetEvent(true); 

    void DisplayThread1() 
    { 
     while (true) 
     { 
      thread2Step.WaitOne(); 
      Console.WriteLine("Display Thread 1"); 
      Thread.Sleep(1000); 
      thread1Step.Set(); 
     } 
    } 

    void DisplayThread2() 
    { 
     while (true) 
     { 
      thread1Step.WaitOne(); 
      Console.WriteLine("Display Thread 2"); 
      Thread.Sleep(1000); 
      thread2Step.Set(); 
     } 
    } 

    void CreateThreads() 
    { 
     // construct two threads for our demonstration; 
     Thread thread1 = new Thread(new ThreadStart(DisplayThread1)); 
     Thread thread2 = new Thread(new ThreadStart(DisplayThread2)); 

     // start them 
     thread1.Start(); 
     thread2.Start(); 
    } 

    public static void Main() 
    { 
     MyThreadTest StartMultiThreads = new MyThreadTest(); 
     StartMultiThreads.CreateThreads(); 
    } 
} 
+0

이 답변이 어떻게 질문과 관련이 있는지, 왜 받아 들여지는지 잘 모르겠습니다. 제공된 코드에서 "스레드 간 순환 종속"이 없으며 스택 오버플로 예외가 발생하지 않습니다. – Evk

+0

@Evk - StackOverflowException에 대해서는 확실하지 않지만 순환 적 depedancy가 있으므로이 줄은 dead1.Other = dead2; dead2.Other = dead1; 서로간에 참조를 저장하는이 두 객체에서 스레드 간의 순환 종속성을 생성합니다. –

+0

하지만 이것은 정상적으로 처리되며 제공된 코드에서 문제를 발생시키지 않습니다. 이는 데드락 조건을 시뮬레이트하는 데 사용됩니다. 그리고 질문은'[Synchronization]'속성과 그것의 작동 원리에 관한 것이지만 당신의 답에는이 속성을 전혀 언급하지 않습니다. – Evk