이벤트 소개

이전

대리자와 같은 이벤트는 런타임에 바인딩 메커니즘입니다. 실제로 이벤트는 대리자에 대한 언어 지원을 기반으로 작성됩니다.

이벤트는 어떠한 문제가 발생했다는 사실을 개체가 시스템의 모든 관련 구성 요소에 브로드캐스트하는 방법입니다. 다른 모든 구성 요소는 이벤트를 구독하고 이벤트가 발생할 때 알림을 받을 수 있습니다.

일부 프로그래밍에서 이벤트를 사용했을 수 있습니다. 많은 그래픽 시스템에는 사용자 조작을 보고하는 이벤트 모델이 있습니다. 이러한 이벤트는 마우스 이동, 단추 누름 등의 조작을 보고합니다. 가장 일반적인 시나리오이기는 하지만 이벤트가 사용되는 유일한 시나리오는 아닙니다.

클래스에 대해 발생해야 하는 이벤트를 정의할 수 있습니다. 이벤트로 작업할 때 한 가지 중요한 고려 사항은 특정 이벤트에 대해 등록된 개체가 없을 수 있다는 점입니다. 구성된 수신기가 없는 경우 이벤트를 발생시키지 않도록 코드를 작성해야 합니다.

이벤트를 구독하면 두 개체(이벤트 소스와 이벤트 싱크) 간 결합도 생성됩니다. 더 이상 이벤트에 관심이 없는 경우 이벤트 싱크가 이벤트 소스를 구독 취소하도록 해야 합니다.

이벤트 지원의 디자인 목표

이벤트에 대한 언어 디자인은 이러한 목표를 대상으로 합니다.

  • 이벤트 소스와 이벤트 싱크 간에 최소 결합을 사용하도록 설정합니다. 이러한 두 구성 요소는 동일한 조직에서 작성할 수 없으며 완전히 다른 일정으로 업데이트할 수도 있습니다.

  • 이벤트를 구독하고 동일한 이벤트를 구독 취소하는 작업은 매우 간단해야 합니다.

  • 이벤트 소스는 여러 이벤트 구독자를 지원해야 합니다. 또한 연결된 이벤트 구독자가 없는 경우를 지원해야 합니다.

이벤트의 목표가 대리자의 목표와 매우 유사하다는 것을 확인할 수 있습니다. 따라서 이벤트 언어 지원은 대리자 언어 지원을 기반으로 합니다.

이벤트의 언어 지원

이벤트를 정의하고 이벤트를 구독 또는 구독 취소하는 구문은 대리자에 대한 구문의 확장입니다.

event 키워드를 사용하는 이벤트를 정의하려면

public event EventHandler<FileListArgs> Progress;

이벤트(이 예제의 경우 EventHandler<FileListArgs>)의 형식은 대리자 형식이어야 합니다. 이벤트를 선언할 때 따라야 할 여러 가지 규칙이 있습니다. 일반적으로 이벤트 대리자 형식에는 void 반환이 있습니다. 이벤트 선언은 동사 또는 동사 구여야 합니다. 이벤트가 발생한 문제를 보고할 때는 과거 시제를 사용합니다. 발생하려고 하는 어떤 문제를 보고하려면 현재 시제 동사(예: Closing)를 사용합니다. 종종 현재 시제를 사용하여 클래스가 몇 가지 사용자 지정 동작을 지원함을 나타내기도 합니다. 가장 일반적인 시나리오 중 하나는 취소를 지원하는 것입니다. 예를 들어 Closing 이벤트에는 닫기 작업이 계속되어야 하는지 여부를 나타내는 인수가 포함될 수 있습니다. 다른 시나리오를 통해 호출자는 이벤트 인수의 속성을 업데이트하여 동작을 수정할 수 있습니다. 알고리즘에서 수행하도록 제안된 다음 작업을 나타내는 이벤트를 발생시킬 수 있습니다. 이벤트 처리기는 이벤트 인수의 속성을 수정하여 다른 작업을 강제로 지정할 수 있습니다.

이벤트를 발생시키려면 대리자 호출 구문을 사용하여 이벤트 처리기를 호출합니다.

Progress?.Invoke(this, new FileListArgs(file));

대리자에 대한 섹션에서 설명한 대로 ?. 연산자를 사용하면 해당 이벤트에 대한 구독자가 없을 때 이벤트를 발생시키지 않도록 하기가 쉽습니다.

+= 연산자를 사용하여 이벤트를 구독합니다.

EventHandler<FileListArgs> onProgress = (sender, eventArgs) =>
    Console.WriteLine(eventArgs.FoundFile);

fileLister.Progress += onProgress;

위에 표시된 대로 처리기 메서드는 일반적으로 접두사 'On'과 그다음에 오는 이벤트 이름입니다.

-= 연산자를 사용하여 구독 취소합니다.

fileLister.Progress -= onProgress;

이벤트 처리기를 나타내는 식에 대해 지역 변수를 선언하는 것이 중요합니다. 따라서 구독 취소하면 처리기가 제거됩니다. 대신 람다 식의 본문을 사용한 경우 연결되지 않아 아무 작업도 수행하지 않는 처리기를 제거하려고 합니다.

다음 문서에서는 일반적인 이벤트 패턴 및 이 예제의 다양한 변형에 대해 자세히 알아봅니다.

다음