인생을 코딩하다.

[Java] Strategy Pattern(전략 패턴) 본문

Java

[Java] Strategy Pattern(전략 패턴)

Hyung1 2021. 2. 8. 16:58
728x90
반응형

디자인 패턴의 꽃이라고 하는 전략 패턴을 알아보자. 전략 패턴을 구성하는 세 요소는 꼭 기억해둬야 한다.

  • 전략 메서드를 가진 전략 객체
  • 전략 객체를 사용하는 컨텍스트(전략 객체의 사용자/소비자)
  • 전략 객체를 생성해 컨텍스트에 주입하는 클라이언트(제3자, 전략 객체의 공급자)
  • 즉, 클라이언트가 전략을 생성해 전략을 실행할 컨텍스트에 주입하는 패턴

전략 패턴이란?

동일 계열의 알고리즘을 정의하고, 각 알고리즘을 캡슐화하여 이들을 상호교환이 가능하도록 만든다. 알고리즘을 사용하는 클라이언트와 상관없이 독립적으로 알고리즘을 다양하게 변경할 수 있게 한다.

 

​ 즉, 특정한 기능을 수행하는데 있어서 다양한 알고리즘이 적용될 수 있는 경우에 상황에 따라 필요한 알고리즘을 선택하여 해결할 수 있는 디자인 패턴이다.

trategy

  • 사용할 행위를 추상화한 인터페이스

Concrete Strategy

  • Strategy에서 명시한 행위를 구현한 클래스

Context

  • 전략을 사용하는 역할
  • 필요에 따라 전략을 바꿔 사용할 수 있음

클라이언트는 다양한 전략 중 하나를 선택해서 생성한 후 컨텍스트에 주입한다.

 

예를 보자.

 

군인이 있고 군인이 사용할 무기가 있다.  보급장교가 무기를 군인에게 지급해주면 군인은 주어진 무기에 따라전투를 수행한다. 이것을 전략 패턴에 따라 구분해보면 아래와 같이 된다.

  • 무기 -> 전략
  • 군인 -> 컨텍스트
  • 보급 장교 -> 제 3자, 즉 클라이언트

먼저 다양한 전략을 공통된 방식으로 사용하기 위해 인터페이스를 정의한다.

package DesignPattern.strategyPattern;

public interface Strategy {
    void runStrategy();
}

이제 다양한 전략, 즉 무기를 구현하자. 먼저 총이다.

package DesignPattern.strategyPattern;

public class StrategyGun implements Strategy {

    @Override
    public void runStrategy() {
        // TODO Auto-generated method stub
        System.out.println("탕! 타탕! 탕탕!");

    }

이번에는 검이다.

package DesignPattern.strategyPattern;

public class StrategySword implements Strategy {
    @Override
    public void runStrategy() {
        System.out.println("쳉.. 채쟁챙 챙챙");
    }
}

마지막으로 활까지 구현해 보자.

package DesignPattern.strategyPattern;

public class StrategyBow implements Strategy{
    @Override
    public void runStrategy() {
        System.out.println("슝..쐐액..쉑, 최종 병기");
    }
}

이번에는 무기(전략)을 사용할 군인(컨텍스트)을 구현하자.

package DesignPattern.strategyPattern;

public class Soldier {
    void runContext(Strategy strategy) {
        System.out.println("전투 시작");
        strategy.runStrategy();
        System.out.println("전투 종료");
    }
}

 마지막으로 무기(전략)를조달(생성)해서 군인(컨텍스트)에게 지급(주입)해 줄 보급 장교(클라이언트, 제3자)를 구현하자.

package DesignPattern.strategyPattern;

public class Client {
    public static void main(String[] args) {
        Strategy strategy = null;
        Soldier rambo = new Soldier();

        // 총을 람보에게 전달해서 전투를 수행하게 한다.
        strategy = new StrategyGun();
        rambo.runContext(strategy);

        System.out.println();

        // 검을 람보에게 전달해서 전투를 수행하게 한다.
        strategy = new StrategySword();
        rambo.runContext(strategy);

        System.out.println();

        // 화을 람보에게 전달해서 전투를 수행하게 한다.
        strategy = new StrategyBow();
        rambo.runContext(strategy);
    }
}

출력

위 처럼 전략을 다양하게 변경하면서 컨텍스트를 실행할 수 있다. 단일 상속만이 간으한 자바 언어에서는 상속이라는 제한이 있어 템플릿 메서드보다는 전략 패턴이 더 많이 활용된다.

전략 패턴의 클래스 다이어그램을 보면 개방 폐쇄 원칙(OCP)과 의존 역전 원칙(DIP)이 적용된 것을 짐작할 수 있다.

 

 

장점

  • 재사용이 쉽기 때문에 코드의 중복이 적다.
  • 확장과 유지보수가 쉽다.

단점

  • 사용자는 각 전략이 어떻게 동작하는지 이해하고 사용해야 한다.
  • Concrete Strategy 클래스는 Strategy 인터페이스의 정보를 공유하기 때문에 필요하지 않은 정보를 갖는 경우가 발생한다.
  • 각 전략은 인터페이스를 구현하여 객체로 만들어지기 때문에 전략의 개수만큼 객체가 생성되어야 한다.

출처 :

자바의신

Team-ITDA

728x90
반응형

'Java' 카테고리의 다른 글

[Java]프록시 패턴(Proxy Pattern)  (0) 2021.02.09
[Java] 어댑터 패턴(Adapter Pattern)  (0) 2021.02.08
[Java] ConcurrentHashMap  (0) 2021.01.30
[Java] Fork Join Pool  (0) 2021.01.29
[Java] PriorityQueue(우선순위 큐)  (0) 2021.01.28
Comments