728x90
반응형
정의
- 데코레이터 패턴으로 객체에 추가 요소를 동적으로 더한다.
- 데코레이터를 사용하면 서브클래스를 만들 때 보다 훨씬 유연하게 기능을 확장할 수 있다.
- 너무 많은 종류가 있을때 상속을 쓰게 되면 관리해야 될 객체가 많아진다.
- 예를 들어 음료의 종류가 100개가 넘는다면 100개의 객체를 관리를 해야 될 것 이다. - 그렇기 때문에 데코레이터 패턴을 사용하면 된다.
- 아래는 다크로스트 -> 모카추가 -> 휘핑크림을 추가한 데코레이터 패턴의 모습이다.
구조
기본구조
ConcreateComponent
- component 의 구체화
- 메소드를 추가해 새로운 행동을 추가 할수 있다.
ConcreateComponent
- 각 데코레이터 안에는 Component 객체가 들어 있다.
- 데코레이터에는 구성요소의 레퍼런스를 포함한 인스턴스 변수가 있다.
ConcreateDecorator
- 감싸고 있는 Component 객체용 인스턴스 변수가 있다.
예제 구조
코드
Beverage
package headfirst.patterns.decorator.coffee;
import lombok.Getter;
@Getter
public abstract class Beverage {
String description = "";
public enum Size{TALL, GRANDE, VENTI};
Size size = Size.TALL;
public void setSize(Size size) {
this.size = size;
}
public abstract double cost();
}
Espresso
- Beverage 를 상속받아서 만든다.
- 그렇게 되면 다형성을 가지게 된다.
- 상속을 사용한 이유는 CondimentDecorator 에서 Beverage 를 선언하여 어떤종류의 커피도 받을수 있도록 하기 위함이다.
package headfirst.patterns.decorator.coffee;
public class Espresso extends Beverage {
public Espresso() {
description = "espresso";
}
public double cost() {
return 1.99;
}
}
CondimentDecorator
- Beverage 를 상속받은 이유는 코스트를 내부에서 쉽게 계산하기 위함이다.
- 그래야 모든 값과 비용을 계산 할 수 있다.
- Espresso 의 가격도 알아야 하고 토핑의 가격도 알아야 하기 때문이다.
package headfirst.patterns.decorator;
import headfirst.patterns.decorator.coffee.Beverage;
public abstract class CondimentDecorator extends Beverage {
Beverage beverage;
public abstract String getDescription();
public Size getSize() {
return beverage.getSize();
}
}
Mocha
- 여기서부터 데코레이터를 위한 상속을 받았고
- 생성자에서 Beverage 를 주입받는다. 모카도 결국 Beverage를 상속받았기 때문에
다른 토핑도 들어올수 있게 된다.
public class Mocha extends CondimentDecorator{
public Mocha(Beverage beverage) {
this.beverage = beverage;
}
@Override
public double cost() {
return beverage.cost() + 0.20;
}
@Override
public String getDescription() {
return beverage.getDescription() + ", mocha";
}
}
테스트 코드
Beverage beverage = new Espresso();
System.out.println(beverage.getDescription());
beverage = new Mocha(beverage);
beverage = new Mocha(beverage);
Assertions.assertEquals(beverage.cost(),2.49);
전체코드
https://github.com/rnrl1215/design-pattern/tree/main/src/main/java/headfirst/patterns/decorator
참고:
728x90
반응형
'Design pattern > GoF(HeadFirst)' 카테고리의 다른 글
[HeadFirst] 커맨드 패턴 (0) | 2023.02.10 |
---|---|
[HeadFirst] 옵저버 패턴 (0) | 2022.12.03 |
댓글