[ Effective C++ ] 항목 37 : 어떤 함수에 대해서도 상속받은 기본 매개변수 값은 절대로 재정의하지 말자

Minsu._.Lighting·2023년 12월 9일
0

[ Effective C++ ] 정리 모음집
" C++ 프로그래머의 필독서, 스콧 마이어스의 Effective C++ 를 읽고 내용 요약 / 정리 "

[핵심]

" 가상 함수는 동적 바인딩! 기본 매개변수는 정적 바인딩! "

  • 위와 같은 이유로 상속받은 기본 매개변수 값은 절대 재정의 해서는 안 된다.

💡 예제 - 기화학 도형을 나타내는 클래스

class Shape
{
public:
	enum ShapeColor { Red, Green, Blue };
    
    virtual void draw(ShapeColor color = Red) const = 0;
    ...
};

class Rectangle : public Shape
{
public:

virtual void draw(ShapeColor color = Green) const;
...
};

class Circle : public Shape
{
public

virtual void draw(ShapeColor color) const;
...
}

📌 객체의 정적 타입

Shape* ps;							// 정적 타입 = Shape*
Shape* pc = new Circle;				// 정적 타입 = Shape*
Shape* pr = new Rectangle;			// 정적 타입 = Shape*
  • 프로그램 소스 안에 선언문을 통해 그 객체가 갖는 타입

📌 객체의 동적 타입

Shape* ps;							// 정적 타입 = Shape*	// 동적 타입은 없음
Shape* pc = new Circle;				// 정적 타입 = Shape*	// 동적 타입 Circle*
Shape* pr = new Rectangle;			// 정적 타입 = Shape*	// 동적 타입 Rectangle*

ps = pc;							// ps의 동적 타입은 이제 Circle*
ps = pr;							// ps의 동적 타입은 이제 Circle*
  • 현재 그 객체가 진짜 무엇인지에 따라 결정되는 타입
    - "특별히 동작해야 한다면 직접 구현 해! 그게 아니라면 기본 구현 버전을 사용 해!

📌 가상 함수는 동적 바인딩! 하지만 기본 매개 변수는 정적 바인딩!

pc->draw(Shape::Red);		// Circle::draw(Shape::Red)
pr->draw(Shape::Red);		// Rectangle::draw(Shape::Red)
  • 매개변수에 아무것도 전해주지 않고 기본 매개 변수를 사용하면?
pr->draw();					// Rectangle::draw(Shape::Red) 호출!

- Rectangle::draw의 기본 매개변수는 Shape::Green 이지만, pr의 정적 타입이 Shape* 이므로 기본 매개변수도 Shape::draw()의 기본 매개변수를 따라 Shape::Red로 넘겨진다!

📌 기본 클래스, 파생 클래스의 기본 매개 변수를 같은 값을 주면?

class Shape
{
public:
	enum ShapeColor { Red, Green, Blue };
    
    virtual void draw(ShapeColor color = Red) const = 0;
    ...
};

class Rectangle : public Shape
{
public
	virtual void draw(ShapeColor color = Red) const;
    ...
};
  • 코드 중복에 의존성까지 걸린다
    - Shape::draw 함수의 기본 매개변수 값이 바뀌면 파생 클래스 모두를 바꿔야 한다

📢 비가상 인터페이스 관용구를 사용해 해결!

class Shape
{
public:
	enum ShapeColor { Red, Green, Blue };
    
    void draw(ShapeColor color = Red) const
    {
    	doDraw(color);
    }
    ...
private:
	virtual void doDraw(ShapeColor color) const = 0;
};

class Rectangle : public Shape
{
public:
	...
private:
	virtual void doDraw(ShapeColor color) const;
    ...
};
profile
오코완~😤😤

0개의 댓글

관련 채용 정보