Decorator

2022. 3. 9. 00:00CSharp/Design Pattern

반응형

주어진 상황 및 용도에 따라 어떤 객체에 책임을 덧붙이는 패턴으로, 기능 확장이 필요할 때 서브클래싱 대신 쓸 수 있는 유연한 대안이 될 수 있다.

 

옷을 입는 것데코레이터의 좋은 예

추우면 스웨터를 입고 위에 재킷을 입을 수도 있다.

또 비가 오면 비옷을 입을 수 있다. 

모든 옷은 기본 행동을 확장 하지만 자신의 일부는 아니다. 

필요하지 않으면 쉽게 옷을 벗을 수 있다. 

https://refactoring.guru/design-patterns/decorator

 

class diagram

https://refactoring.guru/design-patterns/decorator

 

  • 코드를 손상시키지 않고 런타임에 개체에 추가 동작을 할당할 수 있어야 하는 경우 데코레이터 패턴을 사용
  • 상속을 사용하여 개체의 동작을 확장하는 것이 어색하거나 불가능할 때 데코레이터 패턴을 사용

 

아래 코드는 대검과 단검에 추가적인 효과를 주어 무기를 강화 시키는 것이다.

독과 대못을 추가 할 수 있고 이 기능을 구현 하기 위해 Decorator 를 사용한다. 

 

Component 에 해당 하는 무기 구현

public interface IWeapon
{
    void Attack();
}

public class BastardSword : IWeapon
{
    public void Attack() => Console.WriteLine("대검으로 공격");
}
public class Dagger : IWeapon
{
    public void Attack() => Console.WriteLine("단검으로 공격");
}

Decorator 에 해당 하는 추가 효과 구현 (독과,대못...)

// Decorator 는 Component 에 해당하는 IWeapon 인터페이스를 구현한다. 
public abstract class WeaponDecorator : IWeapon
{
    public abstract void Attack();
}

public class Poison : WeaponDecorator
{
    private readonly IWeapon _weapon;

    public Poison(IWeapon weapon)=> _weapon = weapon;

    public override void Attack()
    {
        Console.Write("독묻은 ");  
        _weapon.Attack() ;
    }
}

public class Spike : WeaponDecorator
{
    private readonly IWeapon _weapon;

    public Spike(IWeapon weapon) => _weapon = weapon;

    public override void Attack()
    {
        Console.Write("대못박힌 ");
        _weapon.Attack();
    }
}

 

사용법

IWeapon weapon = new Poison(new Spike(new Dagger()));
weapon.Attack();

weapon = new Spike(new BastardSword());
weapon.Attack();
// output
독묻은 대못박힌 단검으로 공격
대못박힌 대검으로 공격

 

관련영상

https://youtu.be/GBeyfYz2Qws

 

 

반응형

'CSharp > Design Pattern' 카테고리의 다른 글

Flyweight  (0) 2022.03.11
Facade  (0) 2022.03.10
Composite  (0) 2022.03.08
Bridge  (0) 2022.03.07
Adapter (Structural Pattern)  (0) 2022.02.28