[Design Pattern] 7. Adaptor Pattern
이번에는 어댑터 패턴. 어댑터 패턴은 굉장히 쉬운 듯 하면서도 신경 쓸 게 많은 것 같다.
- 어떤 클래스(Adaptee)의 인터페이스를 다른 클래스의 인터페이스(Target)에 맞춰서 사용하고 싶을 때 사용.
장점 1. 어댑터는 Target의 속성(다형성 등)을 그대로 사용할 수 있다.
종류로는 두 가지가 있는 듯하다. 첫번째는 클래스 어댑터, 두번째는 객체 어댑터. 구현방식의 차이가 있을 뿐이다. 이름 그대로 직관적.
-
클래스 어댑터 : 다중 상속을 사용하여 두 클래스(Adaptee, Target)의 인터페이스와 구현 모두를 상속받아 Target 인터페이스에 Adaptee 구현을 끼워맞춰 사용하는 형식.
-
객체 어댑터 : Target을 상속받아 인터페이스를 상속받은 후, Adaptee를 객체로 가지고 있음으로써 Adaptee의 구현을 사용하는 형식.
다음은 예제!
// 인터페이스를 변경하고자 하는 클래스
// adaptee
class Human{
public:
virtual void officialLanguage(){
cout<<"officialLanguage"<<endl;
}
};
// 1. 클래스 어댑터 구현
// target
class Elf{
public:
virtual void quenya(){
cout<<"quenya"<<endl;
}
};
// adapter
class HumanToElfAdapter : public Elf, public Human{
void quenya() override {
Human::officialLanguage();
}
};
// 2. 객체 어댑터 구현
// target
class Orc{
public:
virtual void orcish(){
cout<<"orcish"<<endl;
}
};
// adapter
class HumanToOrcAdapter : public Orc{
public:
HumanToOrcAdapter() : _human(new Human) {}
void orcish() override {
_human->officialLanguage();
}
private:
Human* _human;
};
int main()
{
// 클래스 어댑터
unique_ptr<Elf> rebirth(new HumanToElfAdapter());
rebirth->quenya();
// 객체 어댑터
unique_ptr<Orc> rebirth2(new HumanToOrcAdapter());
rebirth2->orcish();
return 0;
}