본문 바로가기
C++

클래스 멤버함수는 // virtual의 원리 // 다중상속 * 다시 봐야될듯.ㅠ

by 상레알 2009. 2. 5.

-함수 포인터 -
○함수 포인터는 함수의 시작 지점의 주소를 포함하는 변수이다.

○프로그램을 컴파일할 때 프로그램에 있는 각 함수의 시작 지점을 생성하고 프로그램이 링크되면 함수가 참조될 때마다 호출되는 물리적 주소에 해당
한다.

○시작 지점은 주소이기 때문에 포인터 변수가 포인터를 이용하여 함수를 호출하는 것이 가능하다.

○함수를 가리키는 변수를 만들기 위해서는 함수의 반환 형과 같은 형을 가지는 포인터를 선언하며, 이포인터는 어떠한 매개변수 보다도 앞에 선언해야 한다..

int (*p)(int a, int b) ;     - *p 주위에 있는 괄호는 C의 우선 순위 규칙 때문에 반드시 필요하다.





- 객체생성시  :  객체가 생성되면, 멤버 변수는 객체내에 존재한다. 그러나 멤버 함수는 메모리으 한 공간에 존재                     하면서, 모든 객체가 공유하는 형태를 취한다.


가상함수 : 가상함수가 하나라도 잇으면 가상테이블이 생성이 되서 거기에 저장이되서  
              가상테이블을 참조하여 호출한다.

상속관계에 잇을 경에는   예를 들어 A클래스의 a 라는 함수를 가상함수로써 쓰고 B클래스도 a라는 가상함수 있다고 생각을 해보자   그리고 B클래스는 A클래스를 상속한다라고 가정을하면  상속시에 B클래스에는 a라는 함수가 오버라이딩으로 재정의 될것이다 그러면   오버라이딩 되었을 때 객체 호출 과정을 보면 가상함수 테이블에는 A클래스의 a의 정보는 없고 B클래스의 a정보가 멤버 가 된다. 그래서 A클래스의 a함수가 B클래스의 멤버가 된다.

단점: 메모리공간 소모 /// 속도가 느리다.(몸으로 느낄정도는 아니지만;;)


다중상속

다중 상속이란, 하나의 Derived  클래스가 둘 이상의 Base 클래스를 상속하는 것을 말한다.
-다중 상속을 하게되면 클래스들의 관계가 복잡해지고 관리하기에도 어려움이 따른다. 즉. 득보다 실이 더 큰 문법이다.
-다중 상속을 해야만 해결할 수 있는 문제들이 존재한다면 해야겟지만 그런 문제는 존재하지 않는다는군..-_-(왜만들엇지...)

ex) class C : public A, pulbic B

다중 상속을 할경우에는  범위 지정연산자를 사용하여 정확하게 어떠한 함수를 호출할 것인지 명시해 줘야한다.
ex)
AAA::String();
BBB::String();


Virtual Base 클래스

ex)

class A{}

class B : pulbic A{}   // virtual public A

class C: pulbic A{}   // vurtual public A

class D: pulbic B, : pulbic C{}

---------------------------------------

위에 예를 보면 D클래스는 B 클래스와 C 클래스 두 클래스를 다중 상속하고 있다. 그런대 B클래스와 C클래스는 각각 A 클래스를 상속하고 있다 .  그러면 D 클래스는 A클래스를 2번 상속하게 된다  -_-;;
그러므로 컴파일 오류를 발생시키고 만다  위의 문제는 간접경로를 통해 하나의 클래스를 두번이나 상속했기 때문이다. 따라서 이해 대한 해결책은 A클래스를 한번만 상속시키면 되는것이다.
이러한 용도로 사용되는것이 Virtual 상속이다.

주석일 달린대로 상속을 바꾸면  B클래스와 C클래스를 다중상속한다 하더라도 A클래스 안에 존재하는 멤버는 한번만 상속이 이루어진다. 이것이 virtual 상속을 하는 이유이다