Notice
Recent Posts
Recent Comments
«   2024/04   »
1 2 3 4 5 6
7 8 9 10 11 12 13
14 15 16 17 18 19 20
21 22 23 24 25 26 27
28 29 30
Archives
Today
Total
관리 메뉴

DeFacto-Standard IT

헷갈리는 패턴들 - Strategy, Visitor Pattern 본문

Design Pattern/References

헷갈리는 패턴들 - Strategy, Visitor Pattern

defacto standard 2018. 5. 1. 01:08

Strategy Pattern


1 : Many 관계와 같다. 객체의 타입을 하나로 다루면서 이해 다양한 연산을 적용해야할 때, Strategy Pattern을 활용하면 적절하다.


예를 들면, Video 클래스가 있다고 가정하자. 이 클래스는 동영상 파일을 의미한다.


동영상에는 Mpeg, Avi 등 여러 포맷이 존재하고, 표현하는 방법이 모두 다르다. 따라서 MpegVideo, AviVideo 등 파생 클래스가 존재한다.


전부 다르지만 Video Interface(혹은 class)를 상속받아 캡슐화하고, 추상화하여 하나의 Video로 다룰 때 유용하다. 





Visitor Pattern

Many : Many 관계와 같다. 위에서 Video 뿐만아니라 Audio까지 다루게 된다고 가정해보자.


Audio 역시 다양한 포맷이 존재할 것이다. 


만약 Strategy Pattern을 계속해서 사용한다면, Audio 라는 개념을 만들고 그 아래에 또다시 MpegAudio 등의 클래스를 여러개 만들어야 할 것이다.


Mpeg포맷만을 두고 보자. Mpeg을 지원하는, MpegVideo, MpegAudio 이라는, 2개의 클래스가 존재하게 된다.


이를 Visitor Pattern으로 구현한다면, Strategy Pattern을 사용할 때 처럼 여러 개의 클래스를 만들 필요가 없어진다.


MpegMedia 클래스를 정의하고, 이 안에 VideoVisitor, AudioVisitor를 인자로 받아 구현하는 로직을 정의할 것이다.


VideoVisitor는 Mpeg을 지원하는 Video에 관련된 로직이 구현되어 있을 것이고

AudioVisitor는 Mpeg을 지원하는 Audio에 관련된 로직이 구현되어 있을 것이다.






만약 구현해야 하는 포맷이 N(Mpeg, Avi 등)개라고 가정하고, 구현해야하는 매체(Video, Audio 등)가 M개라고 가정하자.

매체 M은 모든 포맷 N을 지원한다고 가정한다.


각 패턴에서 사용되는 클래스의 갯수를 계산해보자.


Stategy Pattern을 사용했을 때, 

Strategy : Strategy Interface M개, ConcreteStrategy M 1개당 N개

= M+M*N

= M(N+1) 개의 클래스가 필요하다.


Visitor Pattern을 사용했을 때, 

Element  : Element Interface 1개 + ConcreteElement N개

Visitor    : Visitor Interface 1개 + ConcreteVisitor M개

= 1 + N + 1 + M

= 2 + M + N 개의 클래스가 필요하다

물론, ConcreteVisitor 하나 당 메서드의 갯수는 ConcreteElementN의 갯수만큼 존재하기 때문에, ConcreteStrategy보다 더 많을 것이다.






Strategy Pattern은 클래스 자체의 소스코드가 짧아져 클래스의 역할을 분명히 할 수 있고, 관계파악이 빨라 의도가 분명하게 드러난다. 

하지만 상위 클래스가 늘어난다면, 서브 클래스 역시 늘어나게 된다.


Visitor Pattern은 Visitor가 Element의 갯수에 따라 메서드가 많아진다.

하지만 관리해야 할 클래스의 갯수 자체는 획기적으로 줄어들어든다.







개인적으로는 Visitor보단 Strategy를 더 선호한다. 


Strategy의 난이도는 기본 수준이기 때문에, 초보 프로그래머들도 쉽게 구현자의 의도를 파악할 수 있기 때문이다.

또한, 클래스 내에 메서드가 많아지면 해당 클래스의 역할을 파악하는 것이 쉽지 않다.

그리고 실질적으로 Strategy가 불편할 정도로 많이 늘어난 경험을 한적이 없다.


Visitor의 경우, 모든 Visitor가 모든 Element들에 대해 신경을 써야 하는 비용도 있다.

그리고 무엇보다, 자칫하면 의도가 명확하지 않아 '왜 이렇게 복잡하게 구현했을까'라는 생각이 들 수 있다.

Comments