2011-07-18 4 views
3

BackgroundWorker을 사용하는 것과 약간 다르게 사용하고 있습니다.DoWork의 백그라운드 작업자 변수 지정

일반적으로 일부 그래픽 컨트롤을 업데이트하기 위해 BW를 사용하고 DoWork 메서드에서 필요한 모든 작업을 수행하고 결과를 반환하고 RunWorkerCompleted 이벤트 처리기에 할당합니다.

여기서는 일부 계산 결과 (DB 쿼리)를 현재 Window의 개인 변수 _myList에 할당하려고합니다.

나는 DoWork 메서드에서 목록을 할당 할 수 있다는 것을 알고 매우 놀랐다. 그리고 나는 정말로 놀랐다.

정상인지 또는 어떤 이유로 권장되지 않았는지 알고 싶었습니까?

답변

4

변수에 할당 할 수있는 권한은 크로스 스레드 작업에 대한 감시가 없으므로 해당 요소 만 UI 요소입니다.

권장하는 경우 멀티 스레드 동기화 영역으로 이동하고 있습니다.

보통 당신은 경쟁 조건 같은 일을 방지하기 위해, 그것을 사용하기 전에 리소스에 대한 액세스를 잠 그려면 :

static object Locker = new object(); 

lock (Locker) 
{ 
    // variable assignment in here. 
} 

, 당신의 말에 다음에 설정에서 귀하의 사용이 기본 인 경우 당신이 읽은 배경 작업자 덩어리, 그러면 당신은 이것을 안전하게 할 수 있습니다. 그러나 다른 물건이 그것에 쓰려고 시도하거나 변수 내용을 검사하기 전에 변수 내용을 검사하는 코드가 있으면 경쟁 조건이 시작됩니다.

1

이것은 정상적으로 정상입니다. 컨트롤을 만든 스레드와 다른 스레드에서 컨트롤에 액세스 할 수 없습니다. 다른 모든 변수의 경우 그러한 제한이 없습니다.
그러나 스레딩과 관련된 다른 문제에주의해야합니다. 같은 변수에 액세스하는 두 개의 스레드가있는 경우 액세스가 동기화되지 않으면 문제가 발생할 수 있습니다.

0

"오프라인"으로 데이터를 동기화해도 아무런 문제가 없으므로이 프로세스가 진행되는 동안 사용자가 계속 UI를 사용할 수 있다고 판단하면 이야기 할 수 있습니다.

나는 이것을 많이했다. 특히 모바일 응용 프로그램을 개발할 때.

2

변수가 UI 컨트롤과 같은 CrossThreading으로부터 보호되지 않기 때문에 원하는 기능입니다.

두 개의 개별 스레드가 동일한 객체에 액세스하지 않도록주의해야합니다. 특히 List 또는 Dictionary와 같이 더 복잡한 데이터 구조 인 경우 매우 이상한 결과와 예외가 발생할 수 있습니다.

개체에 대한 액세스를 동기화하려면 필요하면 lock 문을 사용할 수 있습니다.

int, uint 등과 같은 값 유형은 이론상 문제가되지 않아야합니다.

This 페이지는 스레딩을위한 좋은 출발점을 제공합니다.

3

필자는 백그라운드 작업자 DoWork 이벤트에서 모든 종류의 변수 (UI 컨트롤뿐만 아니라)에 액세스하지 않도록 항상 노력할 것입니다. 그것은 대부분의 시간 동안 작동하는 것처럼 보일지 모르지만 그것은 100 % 증거가 아닙니다. 변수가 정적이라면 액세스에 문제가 없습니다.

작업자가 작업해야하는 변수가 둘 이상인 경우 작은 클래스 또는 구조체를 만들어 모든 변수를 보유한 다음 DoWork 이벤트에 전달하고 e에서 업데이트 된 값을 반환하는 경향이 있습니다. 배경 작업자의 결과입니다. 그런 다음 WorkerCompleted 이벤트에서 그에 따라 로컬 변수를 업데이트 할 수 있습니다.

관련 문제