호환되지 않는 인터페이스 때문에 함께 동작할 수 없는 클래스들을 함께 동작해주도록 변환하는 역할
특징
- 기존의 클래스를 수정하지 않고도 특정 인터페이스를 필요로 하는 코드에서 사용할 수 있게 해줌
- 클래스의 인터페이스를 다른 인터페이스로 변환 가능
- 코드의 재사용성을 높일 수 있음
- 호환성 및 신규 기능 확장 가능
예제
- 못건드리는 라이브러리(OuterTiger) 대신에 가상의 어댑터(TigerAdapter) 생성
- 어댑터(TigerAdapter)는 외부(Animal)를 상속받아 타입 일치시키고 강제 메서드 구현(override)
- TigerAdapter가 OuterTiger를 컴포지션(합성)함
package ch03;
// 추상 클래스 => 상속 가능
public abstract class Animal {
public abstract String getName();
}
package ch03;
// 고양이 Object
// Animal 상속
public class Cat extends Animal {
private String name = "고양이";
// 부모와의 동일 메소드 오버라이드
public String getName() {
return name;
}
}
package ch03;
// 쥐 Object
// Animal 상속
public class Mouse extends Animal {
private String name = "쥐";
// 부모와의 동일 메소드 오버라이드
public String getName() {
return name;
}
}
package ch03;
// 못건드리는 외부 라이브러리
public class OuterTiger {
private String fullname = "호랑이";
public String getFullname() {
return fullname;
}
}
package ch03;
// 계획
// 1. 타입 일치 시키기 => Animal 상속받아서 타입 일치
// 2. OuterTiger 불러오기 => 컴포지션(합성)
// 3. OuterTiger의 getter 가져와서 Animal과의 동일 메소드 오버라이드
// 어댑터
// OuterTiger와 Cat, Mouse 등과의 이질적인 것을 동일하게 맞추는 역할
// TigerAdapter가 OuterTiger를 컴포지션(합성)함
public class TigerAdapter extends Animal{
// 불러와서 컴포지션
private OuterTiger outerTiger;
// 생성자
public TigerAdapter(OuterTiger outerTiger) {
this.outerTiger = outerTiger;
}
// 재정의해서 부모에 있는 동일 메소드 무효화 => 오버라이드, 동적바인딩
@Override
public String getName() {
return outerTiger.getFullname();
}
}
package ch03;
// srp (Single Responsibility Principle)
public class Doorman {
// DIP (Dependency Inversion Principle, 의존성 역전 원칙)
// 이 클래스의 책임
public void 쫓아내(Animal animal) {
System.out.println(animal.getName() + " 쫓아내");
}
}
package ch03;
public class App {
public static void main(String[] args) {
Doorman doorman = new Doorman();
OuterTiger outerTiger = new OuterTiger();
TigerAdapter ta = new TigerAdapter(outerTiger);
Cat cat = new Cat();
Mouse mouse = new Mouse();
doorman.쫓아내(ta);
doorman.쫓아내(cat);
doorman.쫓아내(mouse);
}
}Share article