블로그 이미지
대갈장군

calendar

1 2
3 4 5 6 7 8 9
10 11 12 13 14 15 16
17 18 19 20 21 22 23
24 25 26 27 28 29 30
31

Notice

2010. 6. 18. 00:43 프로그래밍/C#
델리게이트에 대해서 공부하다 보니 공변성 (Covariance)반공변성 (Contravariance) 에 대한 이야기가 나왔다.

공변성과 반공변성... 뭔 소리인가... 라고 생각한다면 당신은 정상인...

수학 쫌 했다는 분들은 알아들을 수도 있겠다만 나는 처음 이 두 단어를 접하고 언어의 한계성을 느꼈다...

아무튼, 공변성과 반공변성은 사실 같은 원리에 근거한 같은 법칙을 말한다. 여기서 같은 원리란, 부모는 자식을 받아들일수 있으나 자식은 부모를 받아들일수 없다는 원칙이다. 쓰다보니 이런 패륜적인 원리일 줄이야... 헐.

일반적으로 자식 클래스는 부모 클래스로 부터 상속을 받아 여러가지 함수 및 멤버 변수를 추가하게 된다. 자, 그렇다면 자식은 양적으로 부모 보다 더 '많이' 가지고 있다. 반면 부모 클래스는 여러 자식들에게 공통으로 나누어 주어야 하므로 '적게' 가지고 있다.

부모/자식 클래스라는 헷갈리는 말 대신, 많다/적다로 표현하면 훨씬 더 이해가 빠르게 될 것이다. 그렇다면 부모 클래스에 자식 클래스를 대입하면 어떻게 되나? 다른 말로 적은 것 (부모)에 많은 것 (자식)을 넣게되면 자식이 가진 몇몇 함수 및 변수는 잘려 나가겠지만 그래도 잘라내면 그만이므로 문제가 없다.

헌데 반대로 자식에 부모를 대입한다면, 즉, 많은 것 (자식)에게 적은 것 (부모)를 대입한다면 문제가 생기는데 왜냐면 부모는 자식이 가지고 있는 것들을 가지고 있지 않기 때문에 '비어있는 공간'이 생기게 되고 이는 호출 오류를 일으킨다. 왜? 없는 것을 호출하니까...

그래서 부모(적은 것)는 자식(많은 것)을 받아들이지만 그 반대는 성립하지 않는다는 것이다.

함수를 살펴보면 "리턴타입 함수이름(인수)" 이런 형태다. 여기서 리턴 타입과 인수가 바로 '대입'이 일어나는 두 곳이다. 자 여기서 바로 공변성과 반공변성이 등장한다... 

일단 리턴타입의 경우 공변성을 가지는데 다른말로 풀어 쓰자면 위에서 설명한 기본 원리인 '부모는 자식을 받지만 그 반대는 성립하지 않는다'는 원칙을 눈으로 볼때 그대로 따른다는 의미다. 

즉, 선언한 델리게이트의 리턴 타입이 부모 클래스라면 자식 클래스 및 부모 클래스 타입을 리턴 타입으로 가지는 모든 함수를 받아준다는 이야기다. 당연히 그 반대는 안되죠오..

이제 남은 것은 '인수'인데, 여기서 이른바 '
반공변성
반공변성'
이 나온다. 말은 참 어려운것 같지만 한번만 풀어서 생각하면 같은 원리다. 이 반공변성은 위에서 말한 리턴 타입의 경우와 정 반대로 동작한다는 의미에서 붙여진 이름이다.

이것은 언제 '인수'가 대입 되는가를 생각해 보면 이해가 된다. 리턴타입의 경우 델리게이트 객체에 함수를 대입할 때 바로 '대입'이 일어나지만 '인수'는 델리게이트 객체에 함수를 대입할 때가 아니라 그 후에 대입된 함수를 호출 할 때 '대입'이 일어난다. 

고로 리턴 타입과는 달리 인수는 비교해야 하는 시점이 호출할 때이므로 델리게이트 객체에 함수를 대입할 때의 인수가 호출 시점의 인수보다 '부모'이어야 한다. 이것이 코드에서 보았을 때는 공변성과 정반대로 보이게 되므로 이름을 반공변성이라고 붙였다만 사실 알고보면 똑같은 원리에 근거한 것이다.

정리하자면 다음과 같이 말할 수 있다.

리턴타입 델리게이트객체(인수) = 리턴타입 함수객체(
);

위의 공식을 보면 좌측 리턴 타입이 우측 리턴 타입보다 큰데 이것은 좌측 리턴 타입이 우측 리턴 타입을 받아준다는 의미고 마찬가지로 우측 인수가 좌측 인수보다 크므로 받아준다는 의미다. 

이런 공변성과 반공변성을 잘 알고 있으면 델리게이트의 활용에 큰 도움이 될듯..







'프로그래밍 > C#' 카테고리의 다른 글

Asynchronous programming  (0) 2017.05.31
C# 이벤트 - 객체 지향적 메시지  (0) 2010.06.25
C# - 제너릭 (Generic) 에 대한 질문  (0) 2010.06.18
델리게이트 - Delegate  (0) 2010.06.17
posted by 대갈장군