전문가를 위한 C++

2025/03/11 ch.10 상속 활용하기

딴짓거리 2025. 3. 11. 18:41

10.3.2 부모 클래스의 소멸자 

소멸자의 호출 과정

1. 현재 클래스에 있는 소멸자의 본문을 실행

2. 현재 클래스의 데이터 멤버를 생성할 때와 반대 순서로 제거

3. 부모 클래스가 있다면 제거

 

#소멸자 앞에는 항상 virtual을 붙여주자. 최소한 부모 클래스에서만이라도

 

업캐스트와 다운캐스트

베이스 클래스로 선언된 변수에 파생 클래스를 대입하면 슬라이싱이 발생

-> 베이스 클래스에는 파생 클래스에서 추가로 정의된 데이터들에 대한 정보가 없기 때문

 

하지만 베이스 클래스로 선언된 포인터나 레퍼런스 변수에 대입된 파생 클래스는 문제 없음. 업캐스트

그 반대의 경우는 다운캐스트. 바람직하지 않음

 

10.4 다형성을 위한 상속

 

순수 가상 메서드와 추상 베이스 클래스

순수 가상 메서드란 클래스 정의 코드에서 명시적으로 정의하지 않는 메서드

순수 가상 메서드가 하나라도 정의된 클래스를 추상 클래스라고 부름

추상 클래스는 다른 코드에서 인스턴스를 생성할 수 없음. 컴파일러는 이 클래스가 객체를 생성하는 데 사용되지 않는다고 판단함

순수 가상 메서드를 지정하려면 메서드 선언 뒤에 =0를 붙임. 구현코드 작성X

 

10.5 다중상속

여러 클래스 상속하기. 클래스를 선언할 때 이름 뒤에 상속할 베이스 클래스를 나열하면 됨

 

다중상속에서 주의할 점

부모클래스들이 같은 이름의 메서드를 가지고 있다면?

파생클래스에서 그 메서드를 사용하면 모호하다는 에러가 발생

-> 업케스트로 강제하거나 스코프 지정해줌

 

같은 클래스를 두번 상속할때도 모호한 상황 발생

 

Dog를 상속한 Bird를 DogBird가 Dog와 동시에 상속하면? 꼬임

 

유명한 다이아몬드 상속

DogBird에서 Animal의 메서드를 호출하면 Dog->Animal 인지 Bird->Animal인지 모호해진다

 

이런경우 최상단의 클래스를 순수 가상 메서드로만 구성된 추상 클래스로 만들면된다. 베이스 클래스에서 호출할 메서드가 없어서 그 수준에서는 모호함이 발생하지 않기 때문

 

이렇게 까다로운 다중 상속을 왜 쓰는?

is-a관계를 맺는 대상이 여러 개인 객체를 정의하기 위해.

가장 적합한 예는 믹스인 클래스를 구현할 때

-> 믹스인 클래스 : 필요한 기능들을 포함하는 상위 클래스

 

C++에서는 오버라이드한 메서드의 리턴 타입을 바꿀 수 있다

단 원래 리턴 타입이 클래스에 대한 포인터나 레퍼런스 타입이고, 리턴 타입은 그 클래스의 파생 클래스에 대한 포인터나 레퍼런스여야 한다. <- 공변 리턴 타입

 

리스코프 치환 원칙<- 자식 클래스가 부모 클래스의 기능을 대체할 수 있어야 한다

 

단 리턴타입을 void*와같은 전혀 관련 없는 타입으로 변경할 수는 없다.

 

 

10.6.2 파생 클래스에 virtual 베이스 클래스 메서드에 대한 오버로드 메서드 추가하기

??

 

생성자도 상속 가능

 

상속한 생성자 가리기

파생 클래스는 베이스 클래스에서 상속한 생성자와 완전히 동일한 생성자를 정의할 수 있다.

베이스 클래스의 생성자를 상속하면 모든 생성자를 한꺼번에 상속한다. 베이스 클래스 생성자 중 일부만 상속할 수는없다.

상속한 생성자는 베이스 클래스와 똑같은 접근 권한을 가진다. using 선언문에 적용된 접근 권한과 관계 없다.

 

 

 

~560p