어댑터 패턴(Adapter Pattern)
- 호환되지 않는 인터페이스들을 연결하는 디자인 패턴
- 주요 구성 요소
- 타겟(Target) : 클라이언트가 사용하려는 새로운 인터페이스
- 어댑티(Adaptee) : 아직 호환되지 않은 기존 클래스/인터페이스
- 어댑터(Adapter) : 타켓 인터페이스를 구현하여 클라이언트 요청을 어댑티로 전달하는 클래스
- 클라이언트(Client) : 특정 작업을 요청하는 클래스
- 용도 및 필요성
- 기존 코드나 라이브러리를 수정하지 않고 새로운 인터페이스를 사용해야 할 때
- 다른 곳에서 개발한 클래스를 현재 시스템에 통합해야 할 때
- 이미 존재하는 클래스를 새로운 인터페이스로 감싸서 사용자가 편리하게 이용할 수 있도록 할 때
- 사용 방법
- 상속(extends)을 이용한 클래스 어댑터 패턴
- 객체(composition)을 이용한 객체 어댑터 패턴
- 장점
- 기존 코드(Adaptee)를 변경하지 않고 원하는 인터페이스(Target)를 구현하는 객체를 만들어 재사용이 가능 → 개방-폐쇄 원칙(OCP) 준수
- 기존 코드와 인터페이스 변환 작업을 분리하여 관리 가능 → 단일 책임 원칙(SRP) 준수
- 단점
- 클래스 수가 증가하고 구조가 복잡해질 수 있다.
객체 어댑터 패턴
// 고래 인터페이스
public interface Whale {
void swim();
void communicate();
}
// 돌고래 인터페이스
public interface Dolphin {
void swim();
void speak();
}
// 고래 객체
public class BlueWhale implements Whale {
@Override
public void swim() {
System.out.println("Blue whale swims gracefully.");
}
@Override
public void communicate() {
System.out.println("Blue whale communicates with low-frequency sounds.");
}
}
// 어댑터: 돌고래를 고래로 변환
public class DolphinAdapter implements Whale {
private Dolphin dolphin;
public DolphinAdapter(Dolphin dolphin) {
this.dolphin = dolphin;
}
@Override
public void swim() {
dolphin.swim();
}
@Override
public void communicate() {
dolphin.speak();
}
}
// 클라이언트 코드
public class AdapterExample {
public static void main(String[] args) {
// 고래 객체 사용
Whale blueWhale = new BlueWhale();
blueWhale.swim();
blueWhale.communicate();
System.out.println("-----");
// 돌고래 어댑터를 사용하여 돌고래 객체를 고래로 변환하여 사용
Dolphin dolphin = new Dolphin() {
@Override
public void swim() {
System.out.println("Dolphin swims playfully.");
}
@Override
public void speak() {
System.out.println("Dolphin speaks in high-pitched clicks.");
}
};
Whale dolphinAdapter = new DolphinAdapter(dolphin);
dolphinAdapter.swim();
dolphinAdapter.communicate();
}
}
// 결과
Blue whale swims gracefully.
Blue whale communicates with low-frequency sounds.
-----
Dolphin swims playfully.
Dolphin speaks in high-pitched clicks.
클래스 어댑터 패턴
Java에서 클래스 어댑터 패턴을 구현하기 위해 다중 상속이 필요하므로 주로 객체 어댑터 패턴이 사용되며 C++과 같이 다중 상속을 지원하는 프로그래밍 언어에서만 구현할 수 있다.
// 고래 인터페이스
public interface Whale {
void swim();
void communicate();
}
// 돌고래 인터페이스
public interface Dolphin {
void swim();
void speak();
}
// 고래 객체
public class BlueWhale implements Whale {
@Override
public void swim() {
System.out.println("Blue whale swims gracefully.");
}
@Override
public void communicate() {
System.out.println("Blue whale communicates with low-frequency sounds.");
}
}
// 돌고래 어댑터 클래스 (클래스 어댑터 패턴)
public class DolphinAdapter extends BlueWhale implements Dolphin {
@Override
public void speak() {
System.out.println("Dolphin speaks in high-pitched clicks.");
}
}
// 클라이언트 코드
public class AdapterExample {
public static void main(String[] args) {
// 고래 객체 사용
Whale blueWhale = new BlueWhale();
blueWhale.swim();
blueWhale.communicate();
System.out.println("-----");
// 돌고래 어댑터 클래스를 사용하여 돌고래 객체를 고래로 변환하여 사용
Dolphin dolphin = new DolphinAdapter();
dolphin.swim();
dolphin.speak();
}
}
'Computer Science > Design Pattern' 카테고리의 다른 글
[Design Pattern] 컴포지트 패턴 (Composite Pattern) (0) | 2023.10.08 |
---|---|
[Design Pattern] 팩토리 메소드 패턴 (Factory Method Pattern) (0) | 2023.09.23 |
[Design Pattern] 템플릿 메소드 패턴 (Template Method Pattern) (0) | 2023.09.23 |
[Design Pattern] 싱글톤 패턴 (Singleton Pattern) (0) | 2023.09.23 |
[Design Pattern] SOLID (0) | 2023.09.14 |