아이템18. 상속보다는 컴포지션을 사용하라
2021-10-14 00:00:00
# Effective_Java
- 그냥 상속은 문제가 많다…
- 메서드 호출과 달리 상속은 캡슐화를 깨뜨린다.
- 상위 클래스의 변경으로 하위 클래스에 손을 대지 않아도 오작동할 가능성 있다.
- 그 외에도 상위 클래스를 변경하다가 하위 클래스의 요소와 충돌할 가능성도 있음
컴포지션 - 상속을 피해가자
- 새로운 클래스를 만들고 private 필드로 기존 클래스의 인스턴스를 참조하게 하자.
- 기존 클래스가 새로운 클래스의 구성요소로 쓰인다는 의미에서 컴포지션이라 한다.
- 전달(forwarding): 새로운 클래스의 인스턴스 메서드들은 기존 클래스에 대응하는 메서드를 호출해 그 결과를 반환한다.
- 새로운 클래스의 메서드를 전달 메서드라 한다.
- 컴포지션을 사용할 대부분의 상황에서 상속을 사용하면 내부 구현을 불필요하게 노출하는 꼴이다.
- 클라이언트가 노출된 내부에 직접 접근할 수도 있다. (서버 클라이언트의 그 클라이언트 아님 주의)
- 써야할 자식 클래스의 메서드를 사용하는게 아니라 실수로 비슷한 이름의 상위 클래스의 메서드를 사용해버리면 안되니깐~
wrapper class (Decorator pattern)
1 | import java.util.Collection; |
1 | public class ForwardingSet<E> implements Set<E> { |
- Set의 인스턴스를 인수로 받는 생성자를 제공한다.
- 임의의 Set에 계측(instrumental) 기능을 덧씌워서 새로운 Set으로 만드는 것이 핵심!
- 콜백 프레임워크에서는 맞지 않다.
핵심 정의
- 상속은 강력하지만 캡슐화를 해친다.
- 그냥 예외를 두지 말고 상속 대신 컴포지션을 사용해라
- 래퍼 클래스는 하위 클래스보다 견고하고 강력하다.