접근 가능한 멤버는 오직 참조변수의 type에 의해서만 결정된다.(실제로 뭘 가리키고 있는지는 중요하지 않음)

부모는 자식을 가리킬수 있으나 (이것이 upcasting - 자식object가 부모의type으로 casting 됨)
자식은 부모를 가리킬 수 없다. ( as 키워드를 사용해 casting 하면 문법적으론 가능하나 부모class에 없는 함수 call시 런타임시 심각한 오류 발생)

downcasting 은 자식이 부모를 가리키는 것이 아니라 upcasting 된 참조변수를 원래의 type으로 되돌리는 것이다.

upcasting은 implicit 하게 가능하나
downcasting 은 as 키워드를 사용해 explicit 하게 하여야 한다.
이는 참조변수가 실제로 어떤 object 를 가리키게 될지 compile time에는 알 수 없기 때문인 것으로 보인다.

as 키워드는 앞에 있는 참조변수가 가리키는 object 를 뒤의 타입으로 casting 해주는 역할을 한다.

예)
부모클래스 Parent 와 자식클래스 Child가 있다고 하자.

1.upcasting(부모가 자식 가리키기)
Parent pa = new Child();

단, pa 에서는 Parent 에 있는 멤버만 접근 가능

2.downcasting
Parent pa = new Child();
Child ch = pa as Child;

pa 에서는 Parent에 있는 멤버 접근 가능
ch 에서는 Child에 있는 멤버 접근 가능
as Child를 빼먹을시 컴파일 에러 발생 ( downcasting 은 implicit 하게 되지 않음 )

<is 키워드>
downcasting 전에 반드시 is 키워드를 사용하여 점검해 보는 것이 좋다.
Parent pa = new Child();
Child ch = null;
if ( pa is Child )
    ch = pa as Child;

pa is Child 는 pa가 가리키고 있는 object 가 Child type의 참조변수로 가리킬수 있는지 여부를 나타낸다고 보면 된다.
위의 예에서 pa 가 가리키고 있는 object 의 type은 Child 이고, 이는 Child type의 참조 변수로 가리킬수 있으니 true 가 된다.
as 키워드를 사용해 Child로 casting 할 것이기 때문에 Child type의 참조 변수로 가리킬 수 있는지 검사하는 것은 자연스럽다.
이런 이유로, 특별한 경우가 아니라면 is 의 뒤에오는 type과 as 뒤에오는 type을 일치시켜서 쓰는 경우가 많을 것이다.

또한 위의 예에서 pa is Parent 도 true 가 된다. Parent type의 참조변수로 Child 의 object를 가리킬 수 있기 때문이다.
예)
GrandParent -> Parent -> ChildP 의 상속관계가 있고
GrandParent -> ChildGP 의 상속관계가 있을 때..

GrandParent[] gp = new GrandParent[2];
gp[0] = new ChildP();
gp[1] = new ChildGP();

for(int i=0;i<gp.Length;i++)
{
    if(gp[i] is Parent)
    {
        Parent p = gp[i] as Parent;
        //p로 Parent에 있는 함수를 호출
    }
}

위와 같은 형태로 사용할 수 있다.


3.자식이 부모를 가리키기
Child ch = new Parent() as Child; (as 쓰지 않으면 컴파일 에러 발생. 자식이 부모를 가리킬수는 없으므로)
이 상태에서 ch 로 Child에 있는 멤버함수 호출시 런타임에러발생 



다형성(polymorphism)은 글자 그대로 object 가 여러가지 모양을 가진다는 의미이고
upcasting/downcasting 으로 이루어지며, 보통은 부모클래스는 인터페이스가 되는듯 하다.

'C#, .NET' 카테고리의 다른 글

List 의 정렬 ( Sort() )  (0) 2011.06.17
property  (0) 2011.06.17
public, private, protected 와 상속  (0) 2011.06.17
C#에서 Win32 API 사용하기  (0) 2011.06.08
interface와 abstract class  (0) 2011.06.08
Posted by 휘사마
,