2014-11-19 2 views
1

여러 스레드가있는 싱글 톤 클래스에 액세스하는 데 어려움을 겪고 있습니다.싱글 톤 클래스에 대한 멀티 스레드 액세스

이 문서 내 싱글 스레드 안전을 얻기 위해 나에게 좋은 출발점을 제공했습니다 http://csharpindepth.com/Articles/General/Singleton.aspx 내 싱글 톤 클래스는 병렬 방식으로 그들을 하나의 데이터 단결로 파일 그룹을 치료하지만, 처리하도록되어

.

각 파일의 정보를 사전에 저장하고 각 스레드가 나중에 자신의 파일을 참조 할 수 있도록 고유 한 키 (DateTime 및 난수를 사용하여 생성 됨)를 호출 스레드로 리턴합니다.

public string AddFileForProcessing(FileForProcessing file) 
{ 
    var id = CreateUniqueFileId(); 
    var resultFile = CreateResultFileFor(file); 
    //These collections are written here and only read elsewhere 
    _files.Add(id, file); 
    _results.Add(id, resultFile) 
    return id; 
} 

나중에이 스레드는이 ID를 전달하는 메서드를 호출합니다.

a)는 FileWatcher의 작성 이벤트에 응답하고 AddFileForProcessing 호출 스레드를 생성합니다 :

public void ProcessIncomingFile(object sender, EventArgs e) 
{ 
    var file = ((FileProcessingEventArg)e).File; 
    ThreadPool.QueueUserWorkItem(
    item => 
    { 
     ProcessFile(file); 
    }); 
} 

B)에는 processFile 내부, 내가 추가를

public void WriteProcessResultToProperFile(string id, string[] processingResult) 
{ 
    //locate the proper file in dictionary using id and then write information... 
    File.AppendAllLines(_results[key].FileName, processingResult); 
} 

그 방법

는 클래스 내부에 접근 할 것 사전에 파일을 저장하고 처리를 시작합니다.

private void ProcessFile(FileForProcessing file) 
{ 
    var key = filesManager.AddFileForProcessing(file); 
    var records = filesManager.GetRecordsCollection(key); 

    for (var i = 0; i < records.Count; i++) 
    { 
     //Do my processing here 
     filesManager.WriteProcessResultToProperFile(key, processingResult); 
    } 
} 

두 스레드가 동일한 인스턴스를 사용하고 있다면 두 스레드가 이러한 메서드를 호출 할 때 어떤 일이 발생하지 않습니다.

각 스레드는 다른 매개 변수로 AddFileForProcessing 및 WriteProcessResultToProperFile을 호출합니다. 그것들이 두 가지 다른 호출을합니까?

단일 스레드에 속한 ID로 고유하게 식별되는 파일에서 작동하므로 (즉, 파일에 다중 액세스가 발생하지 않음)이 방법을 그대로 두거나 그래도해야합니까? 내 방법을 "잠궈"?

+1

이 메서드가 사용중인 인스턴스 데이터는 무엇입니까? – Servy

+0

'_files'가 Thred-safe 콜렉션이 아닌 경우, 그 주위에서 잠금을 사용해야합니다. – xxbbcc

+0

열쇠는, "각 스레드는 ** 다른 ** 매개 변수로 호출 할 것입니다."입니다. 1.'_files'는 단일 스레드 또는 다중 스레드로 채워 집니까? 2. 처리를 수행하는 스레드가 시작되기 전에'_files' 만 채워져 있습니까? 3. 각 처리 스레드가'_files'에서 고유 한 ID를 선택하는 것을 어떻게 보장합니까?이 세 가지 시나리오를 모두 공유 할 수 있습니까? –

답변

0

예, 공유 사전에서만 읽는 것이 좋습니다. 또한 정확하게 언급 한 것처럼 다른 파일 인 경우 파일을 병렬로 처리 할 수 ​​있습니다.

The documentation 설명 :

Dictionary<TKey, TValue>만큼 컬렉션이 수정되지 않는 한, 동시에 다수의 독자를 지원할 수 있습니다.

누구나 AddFileForProcessing (잠금 없음)으로 전화 할 수있는 경우 아무 것도 할 수 없습니다. 하지만 WriteProcessResultToProperFile으로 전화를 걸면 문제가 없습니다. 즉, AddFileForProcessing을 병렬로 호출하려는 경우 두 가지 모두 개의 메소드 (실제로는이 사전에 액세스하는 모든 코드 부분)에 잠금이 필요합니다.

관련 문제