문제

이것은 과잉이 아니고 필요한 것 중 하나 일뿐입니까? C#의 상호 배제 및 잠금에 대한 다른 게시물을 검색하고 찾았습니다. 여기 그리고 여기.

예시:
우리의 앱에는 여러 번의 연결 스레드를 회전시키는 기능이 있으며이 스레드 내부에는 다음을 사용합니다. Mutex 그리고 a lock. 그렇지 않을 것입니다 lock 이 코드 섹션에 대한 액세스를 차단하고 방지하십시오 connect 다른 스레드에서 업데이트되는 것입니까?

bool connect = false;
Mutex reconnectMutex = new Mutex(false, "Reconnect_" + key);

try
{
   lock(site)
   {
      if(site.ContainsKey(key))
      {
         siteInfo = (SiteInfo)site[key];
         if(reconnectMutex.WaitOne(100, true))
         {
            connect = true;
         }
      }
   }

   if (connect)
   { 
      // Process thread logic
   }
}
catch
{}

reconnectMutex.ReleaseMutex();

더 많은 정보:
이것은 웹 정원에서 실행되지 않는 ASP.NET 웹 서비스에 있습니다.

도움이 되었습니까?

해결책

그 MUTEX (이름이 있기 때문에)는 동일한 기계의 프로세스에도 액세스하는 프로세스를 중지하는 반면, 잠금은 동일한 프로세스에서 다른 스레드 만 중지합니다. 그 코드 샘플에서 왜 두 종류의 잠금이 필요한지 알 수 없습니다. 짧은 시간 동안 간단한 자물쇠를 잡는 것이 좋은 관행 인 것 같습니다. 그러나 훨씬 더 무거운 간호가 Mutx는 아마도 더 오래 (겹치는) 기간 동안 잠겨 있습니다! Mutex를 사용하는 것이 더 간단합니다. 그리고 아마도 아마도 간호 적 잠금 장치가 실제로 필요한지 알아 내기 위해서.

그런데, catch {} 이 시나리오에서 사용하기에 절대적으로 잘못된 것입니다. 당신은 사용해야합니다 finally { /* release mutex */ }. 그들은 매우 다릅니다. 캐치는 그보다 훨씬 더 많은 종류의 예외를 삼킬 것이며, 메모리 손상, 액세스 위반 등과 같은 저수준 예외에 응답하여 마침내 핸들러가 실행되도록합니다.

try
{
    // something
}
catch
{}

// cleanup

당신은 있어야합니다 :

try
{
    // something
}
finally
{
    // cleanup
}

그리고 당신이 회복 할 수있는 구체적인 예외가 있다면, 당신은 그것들을 잡을 수 있습니다.

try
{
    // something
}
catch (DatabaseConfigurationError x)
{
    // tell the user to configure the database properly
}
finally
{
    // cleanup
}

다른 팁

"잠금"은 기본적으로 Montor.enter/Exit의 구문 설탕입니다. Mutex는 다중 프로세스 잠금 장치입니다.

그들은 매우 다른 행동을 가지고 있습니다. 다른 것을 차단하도록 설계되었으므로 동일한 응용 프로그램이나 방법 모두에서 모두 사용하는 데 아무런 문제가 없습니다.

그러나 귀하의 경우, 나는 당신이 세마포어와 모니터를 조사하는 것이 더 나을 것이라고 생각합니다. 프로세스를 가로 질러 고정 해야하는 것처럼 들리지 않으므로이 상황에서 더 나은 선택 일 것입니다.

다른 사람들이 지적한 바와 같이, Mutex는 프로세스를 가로 지르고 로컬 잠금 (모니터)은 현재 프로세스가 소유 한 스레드 만 잠금합니다. 하지만 ...

당신이 보여준 코드에는 꽤 심각한 버그가 있습니다. 끝에 무조건 뮤트를 공개하는 것 같습니다 (즉 reconnectMutex.ReleaseMutex()), 그러나 뮤텍스는 다음에만 취득됩니다 site.ContainsKey() 보고 true.

그래서 만약 site.ContainsKey 보고 false, 그런 다음 뮤텍스를 풀어주는 것이 던질 것입니다 ApplicationException 호출 스레드는 뮤텍스를 소유하지 않기 때문입니다.

당신은 정말로 이것에 답할 수있는 충분한 정보를 제공하지 않았습니다. Earwicker가 이미 언급했듯이 Mutex를 사용하면 동기화 accross 프로세스를 가질 수 있습니다. 따라서 동일한 앱 실행중인 두 인스턴스가 있으면 액세스를 직렬화 할 수 있습니다. 예를 들어 외부 리소스를 사용할 때이 작업을 수행 할 수 있습니다.

이제 사이트에서 동일한 프로세스에서 다른 스레드에 의한 사이트에 대한 사이트를 보호합니다. 이것은 다른 방법 / 스레드가 수행하는 일에 따라 Nessecary 일 수 있습니다. 이제 이것이 그 사이트가 잠겨있는 유일한 곳이라면 그렇습니다. 나는 그것이 과잉이라고 생각할 것입니다.

라이센스 : CC-BY-SA ~와 함께 속성
제휴하지 않습니다 StackOverflow
scroll top