Adapter

适配器

将一个类的接口转换成客户希望的另外一个接口。Adapter模式使得原来由于接口不兼容而不能一起工作的那些类可以一起工作。

适用性

  • 你想使用一个已经存在的类,而它的接口不符合你的需求。
  • 你想创建一个可以复用的类,该类可以与其他不相关的类或不可预见的类(即那些接口可能不一定兼容的类)协同工作。
  • (仅适用于对象Adapter)你想使用一些已经存在的子类,但是不可能对每一个都进行子类化以匹配它们的接口。对象适配器可以适配它的父类接口。

结构

类适配器使用多重继承对一个接口与另一个接口进行匹配。
Adapter类适配器

对象适配器依赖于对象组合。
Adapter对象匹配器

Target - 定义Client使用的与特定领域相关的接口。
Client - 与符合Target接口的对象协同。
Adapter - 对Adaptee的接口与Target接口进行适配。

协作:
Client在Adapter实例上调用一些操作。接着适配器调用Adaptee的操作实现这个请求。

示例

类适配器

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
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
#include <iostream>
//---------------------------------------------------
class Target
{
public:
virtual void request(){}
};
//---------------------------------------------------
class Adaptee
{
public:
void specific_request()
{

std::cout<<"Specific request."<<std::endl;
}
};
//---------------------------------------------------
class Adapter : public Target, public Adaptee
{
public:
virtual void request()
{

specific_request();
}
};
//---------------------------------------------------
class Client
{
public:
Client(Target* target):m_target(target){}
void test()
{

if (!m_target) return;
m_target->request();
}
private:
Target* m_target;
};
//---------------------------------------------------
int main()
{

Adapter adapter;
Client client(&adapter);
client.test();
system("Pause");
}

对象适配器

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
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
#include <iostream>
//---------------------------------------------------
class Target
{
public:
virtual void request(){}
};
//---------------------------------------------------
class Adaptee
{
public:
void specific_request()
{

std::cout<<"Specific request."<<std::endl;
}
};
//---------------------------------------------------
class Adapter : public Target
{
public:
Adapter(){m_adaptee = new Adaptee();}
virtual void request()
{

if (!m_adaptee) return;
m_adaptee->specific_request();
}
private:
Adaptee* m_adaptee;
};
//---------------------------------------------------
class Client
{
public:
Client(Target* target):m_target(target){}
void test()
{

if (!m_target) return;
m_target->request();
}
private:
Target* m_target;
};
//---------------------------------------------------
int main()
{

Adapter adapter;
Client client(&adapter);
client.test();
system("Pause");
}

相关模式

  • Bridge的结构与对象Adapter类似,但是Bridge的出发点不同:Bridge的目的是将接口部分和实现部分分离,从而对它们可以较为容易也相对独立的加以改变。而Adapter则意味着改变一个已有对象的接口。
  • Decorator增强了其他对象的功能而同时又不改变它的接口。因此Decorator对应用程序的透明性比Adapter要好。结果是Decorator支持递归组合,而纯粹使用适配器是不可能实现这一点的。
  • Proxy在不改变它的接口的条件下,为另一个对象定义了一个代理。

[1] 设计模式:可复用面向对象软件的基础