상속

    [Effective Java] 태그 달린 클래스보다는 클래스 계층구조를 활용하라

    태그 달린 클래스는 단점 한가득이다. 열거 타입 선언, 태그 필드, switch문 등 쓸데없는 코드가 많다. 여러 구현이 한 클래스에 혼합되어 있어서 가독성이 좋지 않다. 다른 의미를 위한 코드도 함께 하니 메모리도 많이 사용한다. 필드들을 final로 선언하려면 해당 의미에 쓰이지 않는 필드들까지 생성자에서 초기화해야 한다. 인스턴스 타입만으로는 현재 나타내는 의미를 알 길이 없다. => 태그 달린 클래스는 장황하고, 오류를 내기 쉽고, 비효율적이다. class Figure { enum Shape { RECTANGLE, CIRCLE }; final Shape shape; // 다음 필드들은 모양이 사각형일 때만 쓰인다 double length; double width; // 이 필드는 모양이 원(Cir..

    [Effective Java] 상속을 고려해 설계하고 문서화하라

    상속용 클래스는 내부 구현을 문서로 남겨야 한다. '외부' 클래스를 사용한다는 것은 프로그래머에게 통제권이 없어 언제 어떻게 변경될지 모른다는 의미를 갖는다. 따라서 상속용 클래스를 만들 때는 메서드를 재정의하면 어떤 일이 일어나는지 정확히 정리하여 문서로 남겨야 한다. (public, protected 메서드 중 final이 아닌 모든 메서드) => 어떤 순서로 호출하는지, 각각의 호출 결과가 이어지는 처리에 어떤 영향을 주는지 등 Implementation Requirements API 문서의 메서드 설명에 있는 문구로, 메서드의 내부 동작 방식을 설명하는 곳이다. @implSpec태그를 붙여주면 자바독 도구가 생성해준다. 주의 상속용 클래스의 생성자는 어떤 방식으로든 재정의 가능 메서드를 호출하면 ..

    [Effective Java] 상속보다는 컴포지션을 사용하라

    상속을 사용하면 위험한 이유 (구현 상속) 상위 클래스에서 제공하는 메서드 구현이 바뀐다면 하위 클래스의 로직에도 영향을 줄 수 있다. 상위 클래스에 기능이 추가된 경우 새로운 메서드를 하위 클래스에도 정의해 주어야 한다. 이러한 문제를 해결하기 위해 컴포지션을 사용할 수 있다. 컴포지션 전달 클래스 : 새로운 클래스를 만들고 기존 클래스의 인스턴스를 참조하는 클래스 public class ForwardingSet implements Set { private final Set s; public ForwardingSet(Set s) { this.s = s; } public void clear() { s.clear(); } public boolean contains(Object o) { return s.co..