1、适配器模式 Adapter
原理:创建适配器中间类,将一个已有类的接口转换成客户端期望的目标接口。让两个原本接口不兼容的类可以一起工作,适配器起到 “转换器” 的作用。 使用场景:接入第三方 SDK、新旧系统模块对接、老代码接口改造。
#include <iostream>
using namespace std;
// 目标接口(客户想要调用的接口)
class Target
{
public:
virtual void request() = 0;
virtual ~Target() = default;
};
// 被适配者:旧的、接口不匹配的类
class Adaptee
{
public:
void oldFunc()
{
cout << "旧接口函数执行" << endl;
}
};
// 适配器:继承目标,内部包装被适配对象
class Adapter : public Target
{
private:
Adaptee* adaptee;
public:
Adapter(Adaptee* a) : adaptee(a) {}
void request() override
{
adaptee->oldFunc();
}
};
int main()
{
Adaptee oldObj;
Target* t = new Adapter(&oldObj);
t->request();
delete t;
return 0;
}
一句话归纳:充当转换器,把旧接口转换成目标接口。
2、桥接模式 Bridge
原理:当一个类存在两个可以独立变化的维度,就将抽象部分与实现部分拆分开,二者通过组合而非继承关联;避免多层继承导致子类数量爆炸。 使用场景:图形 + 颜色、跨平台组件、文件格式‑输出设备等二维扩展场景。
#include <iostream>
using namespace std;
// 实现层(变化维度1:颜色)
class Color
{
public:
virtual void fill() = 0;
virtual ~Color() = default;
};
class Red : public Color
{
public:
void fill() override { cout << "红色"; }
};
class Blue : public Color
{
public:
void fill() override { cout << "蓝色"; }
};
// 抽象层(变化维度2:图形)
class Shape
{
protected:
Color* color;
public:
Shape(Color* c) : color(c) {}
virtual void draw() = 0;
virtual ~Shape() = default;
};
class Circle : public Shape
{
public:
Circle(Color* c) : Shape(c) {}
void draw() override
{
cout << "绘制圆形,颜色:";
color->fill();
cout << endl;
}
};
int main()
{
Color* red = new Red();
Shape* cir = new Circle(red);
cir->draw();
delete cir;
delete red;
return 0;
}
一句话归纳:分离抽象与实现,两个维度可独立扩展互不影响。
3、组合模式 Composite
原理:将对象组织成树形层级结构;叶子节点(单个对象)和容器节点(一组对象)对外暴露完全一致的接口,使用者无需区分处理的是单个对象还是集合对象。 使用场景:文件目录树、权限菜单树、组织架构树。
#include <iostream>
#include <vector>
#include <string>
using namespace std;
// 统一抽象组件
class Component
{
public:
string name;
Component(string n) : name(n) {}
virtual void show(int depth) = 0;
virtual void add(Component*) {}
virtual ~Component() = default;
};
//叶子节点(文件,不能包含子节点)
class Leaf : public Component
{
public:
Leaf(string n) : Component(n) {}
void show(int depth) override
{
for (int i = 0; i < depth; i++) cout << "--";
cout << "文件:" << name << endl;
}
};
//容器节点(文件夹,可以包含子节点)
class Composite : public Component
{
private:
vector<Component*> children;
public:
Composite(string n) : Component(n) {}
void add(Component* c) override
{
children.push_back(c);
}
void show(int depth) override
{
for (int i = 0; i < depth; i++) cout << "--";
cout << "文件夹:" << name << endl;
for (auto child : children)
{
child->show(depth + 1);
}
}
};
int main()
{
Composite* root = new Composite("根目录");
Leaf* file1 = new Leaf("readme.txt");
root->add(file1);
root->show(0);
delete root;
delete file1;
return 0;
}
一句话归纳:统一对待单个对象与对象集合,用来构建树形结构。
4、装饰器模式 Decorator
原理:不修改原有对象的代码,动态地一层一层给对象增加额外功能;装饰器类和原始类继承同一个父类,装饰器内部持有原始对象。 使用场景:IO 流包装、报文头部追加、动态添加日志、权限功能。
#include <iostream>
using namespace std;
class Component
{
public:
virtual void operation() = 0;
virtual ~Component() = default;
};
//基础业务对象
class ConcreteComponent : public Component
{
public:
void operation() override
{
cout << "执行基础业务" << endl;
}
};
//装饰器基类
class Decorator : public Component
{
protected:
Component* comp;
public:
Decorator(Component* c) : comp(c) {}
void operation() override
{
comp->operation();
}
virtual ~Decorator() = default;
};
//具体装饰:增加日志
class LogDecorator : public Decorator
{
public:
LogDecorator(Component* c) : Decorator(c) {}
void operation() override
{
cout << "[前置日志] 业务开始" << endl;
Decorator::operation();
cout << "[后置日志] 业务结束" << endl;
}
};
int main()
{
Component* base = new ConcreteComponent();
Component* dec = new LogDecorator(base);
dec->operation();
delete dec;
delete base;
return 0;
}
一句话归纳:动态叠加附加功能,无需修改原对象代码。
5、外观模式 Facade(门面模式)
原理:新增一个高层门面类,内部封装好多个复杂子系统的调用流程;对外只提供一个简单的入口函数,隐藏内部复杂细节。 使用场景:SDK 对外封装、服务启动入口、复杂模块统一调用入口。
#include <iostream>
using namespace std;
//子系统1
class Network
{
public:
void connect() { cout << "建立网络连接\n"; }
};
//子系统2
class Database
{
public:
void open() { cout << "打开数据库\n"; }
};
//子系统3
class Logger
{
public:
void writeLog() { cout << "写入启动日志\n"; }
};
//门面类
class Facade
{
private:
Network net;
Database db;
Logger log;
public:
void startService()
{
net.connect();
db.open();
log.writeLog();
cout << "=== 服务启动成功 ===\n";
}
};
int main()
{
Facade facade;
facade.startService();
return 0;
}
一句话归纳:为一堆复杂子系统,提供一个简单统一的对外入口。
6、享元模式 Flyweight
原理:使用对象池缓存、复用大量重复对象;对象拆分为内部状态(不变,可共享)、外部状态(可变,调用时传入),以此减少内存中对象数量,节约内存资源。 使用场景:字符池、游戏大量重复粒子对象、连接池。
#include <iostream>
#include <unordered_map>
#include <string>
using namespace std;
//享元对象
class Flyweight
{
public:
string innerState;
Flyweight(string s) : innerState(s) {}
void show(string outerState)
{
cout << "共享状态:" << innerState << " ,外部状态:" << outerState << endl;
}
};
//享元工厂,维护对象池
class FlyweightFactory
{
private:
unordered_map<string, Flyweight*> pool;
public:
Flyweight* getFlyweight(string key)
{
if (pool.find(key) == pool.end())
{
pool[key] = new Flyweight(key);
}
return pool[key];
}
};
int main()
{
FlyweightFactory factory;
Flyweight* f1 = factory.getFlyweight("A");
Flyweight* f2 = factory.getFlyweight("A");
f1->show("第一次调用");
f2->show("第二次调用");
cout << f1 << " " << f2 << endl; //地址完全相同,复用同一个对象
return 0;
}
一句话归纳:共享重复对象,降低大量对象带来的内存开销。
7、代理模式 Proxy
原理:创建一个代理对象,代理和真实对象实现同一个接口;客户端访问代理对象,再由代理去调用真实对象,可在前后增加鉴权、日志、缓存、延时加载等附加逻辑。 使用场景:RPC 远程代理、接口权限校验、大对象延迟加载。
#include <iostream>
using namespace std;
//公共抽象接口
class Subject
{
public:
virtual void request() = 0;
virtual ~Subject() = default;
};
//真实对象
class RealSubject : public Subject
{
public:
void request() override
{
cout << "真实对象执行业务逻辑" << endl;
}
};
//代理对象
class Proxy : public Subject
{
private:
RealSubject* realObj;
public:
Proxy()
{
realObj = new RealSubject();
}
void request() override
{
cout << "代理:前置权限校验\n";
realObj->request();
cout << "代理:后置记录调用日志\n";
}
~Proxy()
{
delete realObj;
}
};
int main()
{
Proxy proxy;
proxy.request();
return 0;
}
一句话归纳:通过代理对象控制对真实对象的访问。