Skip to content

Latest commit

 

History

History
175 lines (124 loc) · 6.01 KB

어탭터패턴.md

File metadata and controls

175 lines (124 loc) · 6.01 KB

어탭터 패턴

어탭터 패턴이란?

  • 한 클래스의 인터페이스를 클라이언트에서 사용하고자하는 다른 인터페이스로 변환한다.
  • 어탭터를 이용하면 인터페이스 호환성 문제 때문에 같이 쓸 수 없는 클래스들을 연결해서 쓸 수 있다.
public interface Duck {
          public void quack();
          public void fly();
 }

public class MallardDuck implements Duck {
          @Override
          public void quack() {
                   System.out.println("Quack");
          }   
    
          @Override
          public void fly() {
                   System.out.println("I'm flying");
          }
}
public interface Turkey {
          public void gobble();
          public void fly();
 }

public class WildTurkey implements Turkey {
          @Override
          public void gobble() {
                   System.out.println("Gobble gobble");
          }         

          @Override
          public void fly() {
                   System.out.println("I'm flying a short distance");
          }
 }

Duck 객체가 모자라서 Turkey 객체를 대신 사용해야하는 상황일때, 인터페이스가 다르기 때문에 Turkey 객체를 바로 사용할 수 없다. 사용하기 위해 아래에 어탭터를 만들어본다.

public class TurkeyAdapter implements Duck {
          Turkey turkey;

          public TurkeyAdapter(Turkey turkey) {
                   this.turkey = turkey;
          }

          @Override
          public void quack(){ 
                   turkey.gobble();
          }

          @Override
          public void fly() {
                   turkey.fly();
          }
 }
public class DuckTestDrive {
          public static void main(String[] args) {
                  MallardDuck duck = new MallardDuck();
                  WildTurkey turkey = new WildTurkey();
                  Duck turkeyAdapter = new TurkeyAdapter(turkey);        

                  System.out.println("The turkey says...");
                  turkey.gobble();
                  turkey.fly();
                /*
                  The turkey says...
                  Gobble gobble
                  I'm flying a short distance
                */
              
                  System.out.println("The Duck says...");
                  testDuck(duck);
				/*
				  The Duck says...
                  Quack
                  I'm flying
				*/
              
                  System.out.println("The TurkeyAdapter says...");
                  testDuck(turkeyAdapter);
                /*
                  The TurkeyAdapter says...
                  Gobble gobble
                  I'm flying a short distance
				*/
          }
			
          public static void testDuck(Duck duck){ 
                   duck.quack();
                   duck.fly();
          }
 }

Duck 타입 TurkeyAdapter Class와 Turkey 타입 wildTurkey Class의 결과값이 같은 것을 확인 할 수 있다.

오브젝트 어댑터 VS 클래스 어댑터

  • 오브젝트 어댑터

  • adapter-pattern-1

    • Adapter는 Target 인터페이스의 request() 메소드를 구현 하기 위해 Adaptee 클래스의 method1() 메소드를 사용
    • Client는 Adapter 클래스를 통해 Adaptee를 Target 인터페이스의 구상 클래스처럼 사용할 수 있다.
  • 클래스 어댑터

  • adapter-pattern-2

    • Class Adapter는 다중 상속을 사용한다.
    • Adapter가 Target클래스와 Adaptee클래스를 둘 다 상속하여 Target클래스가 필요한 곳, Adaptee클래스가 필요한 곳 모두 사용 될 수 있다.

    Client : 써드파티 라이브러리나 외부시스템을 사용하려는 쪽

    Adaptee : Client가 사용하려는 써드파티 라이브러리나 외부시스템(위 예제에서는 Turkey)

    Adapter : Client와 Adaptee 중간에서 호환성이 없는 둘을 연결시켜주는 역할을 담당한다. Target Interface를 구현하며, Client는 Target Interface를 통해 Adapter에게 요청을 보낸다. Adapter는 Client의 요청을 Adaptee가 이해할 수 있는 방법으로 전달하고 Adaptee에서 처리가 이루어진다.

    Target Interface : Adapte가 구현(implements)하는 인터페이스이다. 클라이언트는 Target Interface를 통해 Adaptee인 써드파티 라이브러리를 사용하게 된다. (위 예제에서는 Duck)

어댑터 패턴의 장점

  • 관계가 없는 인터페이스 간 같이 사용가능

  • 프로그램 검사가 용이하다.

  • 클래스 재활용성이 증가한다.

  • 상속이 아닌 구성(Composition)을 이용하기 때문에 Adaptee의 모든 서브클래스에서 어댑터를 사용가능

  • Object Adapter Class Adapter
    장점 상속이 아닌 구성을 사용하기 때문에 더 유연하다. Adapter가 Adaptee의 서브 클래스이기 때문에 Adaptee의 행동을 오버라이드 할 수 있다.
    Adaptee 객체를 만들지 않아도 된다.
    단점 Adaptee 객체를 만들어야 사용가능하다. 상속을 이용하기 때문에 한 Adapter 클래스가 특정 Adaptee클래스에만 적용가능하다.
    다중상속이 지원되는 언어에서만 사용가능하다.

참고블로그


한 줄 요약

어댑터 패턴은 호환성이 맞지 않는 클래스를 연관된 관계로 연결하여 사용할 수 있게끔 만들 수 있는 패턴