IT/Programming / / 2023. 4. 27. 09:31

<Effective Java> RULE 20 태그달린 클래스 대신 클래스 계층을 활용하라

반응형

태그달린 클래스

public class Figure {
    enum Shape { RECTANGLE, CIRCLE };
    
    //어떤 모양을 나타냄
    final Shape shape;
    
    //태그가 Rectangle일 때 사용되는 필드
    double length;
    double width;
    
    //태그가 Circle일때 사용되는 필드
    double radius;
    
    //원을 만드는 생성자
    Figure(double radius){
        shape = Shape.CIRCLE;
        this.radius = radius;
    }
    
    //사각형을 만드는 생성자
    Figure(double length, double width){
        shape = Shape.RECTANGLE;
        this.length = length;
        this.width = width;
    }
    
    double area() {
        switch(shape) {
        case RECTANGLE:
            return length * width;
        case CIRCLE:
            return Math.PI*(radius*radius);
            default:
                throw new AssertionError();
        }
    }
}
 

문제점

- enum선언, 태그 필드, switch문등의 코드가 반복되는 클래스 존재

- 서로 다른 기능을 위한 코드가 한 클래스에 모여있으므로 가독성 저하

- 객체를 만들 때 마다 필요없는 기능을 위한 필드도 같이 생성되므로 메모리 요구량 증가

- 새로운 기능을 추가할 때 switch case에 새로운 case를 올바르게 넣어야한다.

- 객체의 자료형만 봐서는 그 객체가 무슨 기능을 하는지 알 수 없다.

- 오류 발생 가능성이 높고 효율적이지 않다!

태그 기반 클래스 계층으로 변환한 결과

abstract class Figure{
    abstract double area();
}

class Circle extends Figure{
    final double radius;
    
    public Circle(double radius) {
        this.radius = radius;
    }
    @Override
    double area() {
        return Math.PI*(radius * radius);
    }
}


class Rectangle extends Figure{
    final double length;
    final double width;
    
    public Rectangle(double length, double width) {
        this.length = length;
        this.width = width;        
    }
    @Override
    double area() {
        return length * width;
    }
}
 

변화된 점

- 태그 기반 클래스의 단점이 사라짐

- 모든 필드에는 final이 붙음

- 최상위 클래스의 소스코드를 보지않고도 독립적으로 소스코드를 작성가능

 

결론

- 태그기반 클래스 사용을 피해야 한다.

- 만약 태그 클래스를 만나게 된다면 리팩토링을 통해 클래스 계층으로 변환할 수 있는지 고민해보자

 

반응형
  • 네이버 블로그 공유
  • 네이버 밴드 공유
  • 페이스북 공유
  • 카카오스토리 공유