2016-08-15 2 views
-1

동시 대기열을 사용하므로 여러 사용자가 자신의 정보를 쓸 수 있습니다. 백그라운드에서 타이머를 사용하여 대기열에있는 모든 것을 시간 기준으로 데이터베이스에 저장합니다. 아래, 내 타이머의 경과 방법에수집을위한 인터록 compareexchange

public void WriteInformation(sting msg) 
{ 
    ConcurrentQueue<MessageQueueItem> oldQueue; 
     do 
     { 
      oldQueue = messageQueue; 
      messageQueue.Enqueue(msg); 
     } 
     while (Interlocked.CompareExchange(ref oldQueue, null, messageQueue) != null); 
} 

, 나는 동시 큐를 재현하고 기존 큐를 처리하고있다 : 내 코드는 타격과 같습니다

var oldQueue = Volatile.Read(ref messageQueue); 
Volatile.Write(ref messageQueue, new ConcurrentQueue<string>()); 

// process the old queue; 
string item; 
if (oldQueue.TryDequeue(out item)) 
{ 
    // compact item and save to DB. 
} 

이 패턴이 맞습니까? 또한 나는 생각하지 않는다

var oldQueue = Volatile.Read(ref messageQueue); 
Volatile.Write(ref messageQueue, new ConcurrentQueue<string>()); 

가 필요하다. 대신 내 WriteInformation 메서드에서와 같이 아래 코드를 사용할 수 있습니다. 이미 messageQueue가 최신 복사본인지 확인하고 있습니다. 맞습니까? WriteInformation 및 messageQueue는 정적입니다. 감사.

var oldQueue = messageQueue; 
messageQueue = new ConcurrentQueue<string>(); 

답변

0

싱글 톤 참조의 변동성에 대해 걱정할 필요가 없습니다. 정적 필드 나 의존성 주입을 통해 액세스하십시오. 올바르게 초기화 된 후입니다. 다른 스레드가 변경되는 것은 대기열의 데이터가 아니라 대기열의 참조입니다. 참조가 초기화 된 후에 절대로 수정해서는 안됩니다.

+0

DB 작업이 매우 느려서 사람들이 데이터를 입력 할 수있는 새 큐를 만들고 타이머 스레드가 백그라운드에서 이전 큐를 처리 할 수 ​​있습니다. – Helic

+0

@Helic 두 번째 줄은 어떤 특별한 문제를 해결합니까? 대기열에 들어간 동일한 대기열에서 소비 할 수없는 이유는 무엇입니까? – zerkms

+0

@zerkms, 너무 자주 WriteInformation 메서드를 호출하면 컬렉션을 너무 많이 잠그고 DB 동작이 지연되고 그 반대의 경우도 발생한다고 생각합니다. – Helic

관련 문제