2012-06-08 3 views
1

오른쪽 스레드에서 타이머 스레드에서 실행 된 메서드를 호출해야합니다. Invoke/BeginInvoke 프로세스가 작동합니다. 데이터 교환을 위해 하나의 스레드 간 데이터 컨테이너를 공유하는 2 개의 스레드가 있습니다. 하나는 대기열을 채우고 하나는 대기열을 처리합니다. 빈 상태 후에 빈 채워지면 큐가 이벤트를 발생시킵니다. 모든 문제는 경과 된 이벤트에 새 스레드를 여는 타이머에 의해 발생합니다. Dispatcher를 사용하여 오른쪽 스레드로 디스패치하지만이 Dispatcher를 제외한 모든 것이 작동합니다. :-)C# 콘솔 응용 프로그램의 디스패처 관련 문제

제발, 문제가 어디 있는지 아시나요?

완전한 테스트 코드는 여기에서 있습니다 : http://pastebin.com/jqYbR9PS.

디버그 출력은 이것이다 :

App Thread ID: 9 
Processor Thread ID: 10 
Processor Dispatcher Thread ID: 10 
The thread '<No Name>' (0x888) has exited with code 0 (0x0). 
Processor QueueListener caller Thread ID: 12 
Processor Dispatcher Thread ID: 10 
Processor invoking ProcessQueue. 
...here shut be processing output... 
Processor invoked ProcessQueue. 
App Thread ID on end: 9 
The thread 'vshost.RunParkingWindow' (0x17c4) has exited with code 0 (0x0). 
The thread '<No Name>' (0x820) has exited with code 0 (0x0). 
The program '[5760] TestingConsoleApplication.vshost.exe: Managed (v4.0.30319)' has exited with code 0 (0x0). 

ProcessQueue이 호출/호출되지 않습니다.

감사합니다.

+3

개인적으로 필자는 이러한 유형의 작업 병렬 라이브러리를 특히 콘솔 응용 프로그램에서 사용합니다. 아마도 그것은 당신을위한 옵션입니까? –

+0

다른 방법으로 타이머 이벤트 스레드를 기본 앱 스레드로 다시 가져 오는 방법이 있습니까? – Fanda

+0

잘 읽으면 평행하게 작업을 수행하는 것이 좋습니다. :-) 내 작업은 데이터베이스 동기화 작업이므로 순차적으로 실행해야합니다. – Fanda

답변

4

Dispatcher가 호출 된 통화를 처리하려면 실제로 Dispatcher.Run()을 호출하여 해당 Dispatcher를 시작해야합니다.

콘솔 응용 프로그램에서 Dispatcher를 사용하는 것은 이상한 일입니다. Dispatcher는 WPF 응용 프로그램에 사용되지만 작동한다고 생각합니다. 당신이 Dispatcher.BeginInvokeShutdown()

를 호출 할 때까지 그것은 예를 들어이 blog post를 참조 루프를 입력합니다 - Dispatcher.Run()에 대한 호출이 반환되지 않습니다

참고.

+0

팁을 사용 해줘서 고맙습니다. 나는 다시 디자인 할 것이다 ... – Fanda

+1

이러한 호출이 구현되는 방법에 대한 Syncrhonization 컨텍스트에서이 기사를 살펴 보자. 그것은 귀하의 재 설계에 도움이 될 수 있습니다 : http://msdn.microsoft.com/en-us/magazine/gg598924.aspx - http://www.codeproject.com/Articles/31971/Understanding-SynchronizationContext-Part-I - http://www.codeproject.com/Articles/32113/Understanding-SynchronizationContext-Part-II – shf301

+0

당신이 건설적인 의심을 썼기 때문에 답으로 답장을 표시합니다. :-) – Fanda

1

Dispatcher.BeginInvoke는 windows 메시지 펌프를 사용합니다. 디스패치하려는 스레드 (processingThread)가 메시지 펌프를 실행하고 있지 않습니다.

해당 스레드에서 메시지 펌프를 실행할 수 있지만 왜 EventWaitHandle 또는 다른 스레드 동기화 개체를 사용하지 않고 그렇게할까요?

또한 코드의 대기열에 대한 작업은 스레드로부터 안전하지 않습니다.

+0

나는 EventWaitHandle을 사용하여 방금 재 설계하고있다. 나는 .NET과 sill을 탐구하는 것에있어서 새로운 것이다. 이것이 주된 이유입니다. 당신의 의견에 감사드립니다. 나는 또한 대기열을 볼 것이다 ... – Fanda

관련 문제