클래스 설계는 타입 설계와 같이 보자(effective c++ 19)

2015. 8. 20. 10:28프로그래밍/Effective C++

728x90
728x90

효과적인 클래스 설계

객체 지향 프로그래밍 언어와 마찬가지로 C++에서 새로운 클래스를 정의한다는 것은 새로운 타입을 하나 정의하는 것과 같다.


고려 사항
문법(syntax)이 자연스럽고 의미구조(semantics)가 직관적이며, 효율적인 구현


클래스 설계에 신경써야 할 부분

새로 정의한 타입의 객체 생성 및 소멸은 어떻게 이루어져야 하는가?

객체 지향 프로그래밍 언어와 마찬가지로 C++에서 새로운 클래스를 정의한다는 것은 새로운 타입을 하나 정의하는 것과 같다.

객체 초기화는 객체 대입과 어떻게 달라야 하는가?

생성자와 대입 연산자의 동작 및 둘 사이의 차이점을 결정짓는 요소이다..
- 초기화와 대입을 헷갈리지 않는 것이 가장 중요하다.

새로운 타입으로 만든 객체가 값에 의해 전달되는 경우에 어떤 의미를 줄 것인가?

어떤 타입에 대해 ‘값에 의한 전달’을 구현하는 쪽은 바로 복사 생성자이다.

새로운 타입이 가질 수 있는 적법한 값에 대한 제약은 무엇으로 잡을 것인가?
- 전부는 아니지만, 클래스의 데이터 멤버의 몇 가지 조합 값만은 반드시 유효해야 한다. (클래스의 불변속성)
- 이 불변속성에 따라 클래스 멤버 함수 안에서 해 주어야 할 에러 점검 루틴이 좌우된다.

기존의 클래스 상속 계통망(ingeritance graph)에 맞출 것인가?

이미 갖고 있는 클래스로부터 상속을 시킨다고 하면, 당연히 여러분의 설계는 이들 클래스에 의해 제약을 받게 된다.
멤버 함수가 virtual의 여부에 따라 상속여부가 결정된다.

어떤 종류의 타입 변환을 허용할 것인가?

- 암시적으로 변환되도록 하고 싶다면 클래스에 타입 변환 함수를 넣어두든가(operator를 통해) 아니면 
인자 한 개로 호출될 수 있는 비명시적 호출 생성자를 넣어 두어야 한다.
- 명시적 타입 변환만 허용하고 싶을 경우에는 해당 변환을 맡는 별도 이름의 함수를 만들되 
타입 변환 연산자 혹은 비명시호출 생성자는 만들지 말아야 한다.

어떤 연산자와 함수를 두어야 의미가 있을까?

- 어떤 것들은 멤버 함수로 적당할 것이고, 또 몇몇은 그렇지 않을 것이다.

표준 함수들 중 어떤 것을 허용하지 말 것인가?

private로 선언할 멤버 함수를 결정한다.

새로운 타입의 멤버에 대한 접근 권한을 어느 쪽에 줄 것인가?
어떤 클래스 멤버를 public, protected, private 영역에 둘 것인가를 결정한다.
- 또한 프렌드로 만들어야 할 클래스 및 함수를 정하고 중첩 클래스에 대해 결정한다.

'선언되지 않은 인터페이스'로 무엇을 둘 것인가?
- 만들 타입이 제공할 보장이 어떤 종류를 결정한다.
- 보장할 수 있는 부분은 수행 성능 및 예외 안전성, 그리고 자원 사용입니다.

새로 만드는 타입이 얼마나 일반적인가?
- 동일 계열의 타입군 전체이라면 새로운 템플릿 클래스를 정의해야 할 것이다.

정말로 꼭 필요한 타입인가?
기존의 클래스에 대해 기능 몇 개가 아쉬워서 파생 클래스를 뽑고 있다면 
차라리 간단하게 비멤버 함수라든지 템플릿을 몇 개 더 정의하는 편이 낫습니다.


728x90
반응형