Skip to content

C++ 设计模式

概述

设计模式是软件设计中常见问题的通用解决方案。它们代表了最佳实践,提供了在特定情况下如何解决常见设计问题的模板。本章介绍常用的设计模式及其在C++中的实现。

🏭 创建型模式

单例模式 (Singleton)

cpp
#include <iostream>
#include <memory>
#include <mutex>
#include <thread>

// 懒汉式单例(线程安全)
class Singleton {
private:
    static std::unique_ptr<Singleton> instance_;
    static std::mutex mutex_;
    
    // 私有构造函数
    Singleton() {
        std::cout << "Singleton实例创建" << std::endl;
    }
    
public:
    // 删除拷贝构造和赋值运算符
    Singleton(const Singleton&) = delete;
    Singleton& operator=(const Singleton&) = delete;
    
    static Singleton* getInstance() {
        std::lock_guard<std::mutex> lock(mutex_);
        if (instance_ == nullptr) {
            instance_ = std::unique_ptr<Singleton>(new Singleton());
        }
        return instance_.get();
    }
    
    void doSomething() {
        std::cout << "Singleton正在工作..." << std::endl;
    }
};

// 静态成员定义
std::unique_ptr<Singleton> Singleton::instance_ = nullptr;
std::mutex Singleton::mutex_;

// 饿汉式单例(线程安全,C++11保证)
class EagerSingleton {
private:
    EagerSingleton() {
        std::cout << "EagerSingleton实例创建" << std::endl;
    }
    
public:
    static EagerSingleton& getInstance() {
        static EagerSingleton instance;  // C++11保证线程安全
        return instance;
    }
    
    EagerSingleton(const EagerSingleton&) = delete;
    EagerSingleton& operator=(const EagerSingleton&) = delete;
    
    void doSomething() {
        std::cout << "EagerSingleton正在工作..." << std::endl;
    }
};

// 工厂方法模式
class Product {
public:
    virtual ~Product() = default;
    virtual void use() = 0;
};

class ConcreteProductA : public Product {
public:
    void use() override {
        std::cout << "使用产品A" << std::endl;
    }
};

class ConcreteProductB : public Product {
public:
    void use() override {
        std::cout << "使用产品B" << std::endl;
    }
};

class Creator {
public:
    virtual ~Creator() = default;
    virtual std::unique_ptr<Product> createProduct() = 0;
    
    void someOperation() {
        auto product = createProduct();
        product->use();
    }
};

class ConcreteCreatorA : public Creator {
public:
    std::unique_ptr<Product> createProduct() override {
        return std::make_unique<ConcreteProductA>();
    }
};

class ConcreteCreatorB : public Creator {
public:
    std::unique_ptr<Product> createProduct() override {
        return std::make_unique<ConcreteProductB>();
    }
};

// 建造者模式
class House {
private:
    std::string foundation_;
    std::string walls_;
    std::string roof_;
    
public:
    void setFoundation(const std::string& foundation) {
        foundation_ = foundation;
    }
    
    void setWalls(const std::string& walls) {
        walls_ = walls;
    }
    
    void setRoof(const std::string& roof) {
        roof_ = roof;
    }
    
    void show() {
        std::cout << "房子: " << foundation_ << " + " << walls_ << " + " << roof_ << std::endl;
    }
};

class HouseBuilder {
public:
    virtual ~HouseBuilder() = default;
    virtual void buildFoundation() = 0;
    virtual void buildWalls() = 0;
    virtual void buildRoof() = 0;
    virtual std::unique_ptr<House> getHouse() = 0;
};

class ConcreteHouseBuilder : public HouseBuilder {
private:
    std::unique_ptr<House> house_;
    
public:
    ConcreteHouseBuilder() {
        house_ = std::make_unique<House>();
    }
    
    void buildFoundation() override {
        house_->setFoundation("混凝土地基");
    }
    
    void buildWalls() override {
        house_->setWalls("砖墙");
    }
    
    void buildRoof() override {
        house_->setRoof("瓦屋顶");
    }
    
    std::unique_ptr<House> getHouse() override {
        return std::move(house_);
    }
};

class Director {
public:
    std::unique_ptr<House> construct(HouseBuilder& builder) {
        builder.buildFoundation();
        builder.buildWalls();
        builder.buildRoof();
        return builder.getHouse();
    }
};

🔧 结构型模式

适配器模式 (Adapter)

cpp
#include <iostream>
#include <string>

// 目标接口
class Target {
public:
    virtual ~Target() = default;
    virtual std::string request() {
        return "Target: 默认行为";
    }
};

// 需要适配的类
class Adaptee {
public:
    std::string specificRequest() {
        return "特殊请求";
    }
};

// 适配器
class Adapter : public Target {
private:
    std::unique_ptr<Adaptee> adaptee_;
    
public:
    Adapter(std::unique_ptr<Adaptee> adaptee) : adaptee_(std::move(adaptee)) {}
    
    std::string request() override {
        return "Adapter: (转换) " + adaptee_->specificRequest();
    }
};

// 装饰器模式
class Component {
public:
    virtual ~Component() = default;
    virtual std::string operation() = 0;
};

class ConcreteComponent : public Component {
public:
    std::string operation() override {
        return "ConcreteComponent";
    }
};

class Decorator : public Component {
protected:
    std::unique_ptr<Component> component_;
    
public:
    Decorator(std::unique_ptr<Component> component) : component_(std::move(component)) {}
    
    std::string operation() override {
        return component_->operation();
    }
};

class ConcreteDecoratorA : public Decorator {
public:
    ConcreteDecoratorA(std::unique_ptr<Component> component) : Decorator(std::move(component)) {}
    
    std::string operation() override {
        return "ConcreteDecoratorA(" + Decorator::operation() + ")";
    }
};

class ConcreteDecoratorB : public Decorator {
public:
    ConcreteDecoratorB(std::unique_ptr<Component> component) : Decorator(std::move(component)) {}
    
    std::string operation() override {
        return "ConcreteDecoratorB(" + Decorator::operation() + ")";
    }
};

// 外观模式
class SubsystemA {
public:
    std::string operationA() {
        return "SubsystemA: 准备就绪!";
    }
    
    std::string operationZ() {
        return "SubsystemA: 开始!";
    }
};

class SubsystemB {
public:
    std::string operationB() {
        return "SubsystemB: 准备就绪!";
    }
    
    std::string operationY() {
        return "SubsystemB: 发射!";
    }
};

class Facade {
private:
    std::unique_ptr<SubsystemA> subsystemA_;
    std::unique_ptr<SubsystemB> subsystemB_;
    
public:
    Facade() : subsystemA_(std::make_unique<SubsystemA>()), 
               subsystemB_(std::make_unique<SubsystemB>()) {}
    
    std::string operation() {
        std::string result = "Facade初始化子系统:\n";
        result += subsystemA_->operationA() + "\n";
        result += subsystemB_->operationB() + "\n";
        result += "Facade命令子系统执行操作:\n";
        result += subsystemA_->operationZ() + "\n";
        result += subsystemB_->operationY();
        return result;
    }
};

🎭 行为型模式

观察者模式 (Observer)

cpp
#include <iostream>
#include <vector>
#include <string>
#include <algorithm>

class Observer {
public:
    virtual ~Observer() = default;
    virtual void update(const std::string& message) = 0;
};

class Subject {
private:
    std::vector<Observer*> observers_;
    std::string state_;
    
public:
    void attach(Observer* observer) {
        observers_.push_back(observer);
    }
    
    void detach(Observer* observer) {
        observers_.erase(
            std::remove(observers_.begin(), observers_.end(), observer),
            observers_.end()
        );
    }
    
    void notify() {
        for (Observer* observer : observers_) {
            observer->update(state_);
        }
    }
    
    void setState(const std::string& state) {
        state_ = state;
        notify();
    }
    
    std::string getState() const {
        return state_;
    }
};

class ConcreteObserver : public Observer {
private:
    std::string name_;
    
public:
    ConcreteObserver(const std::string& name) : name_(name) {}
    
    void update(const std::string& message) override {
        std::cout << name_ << " 收到更新: " << message << std::endl;
    }
};

// 策略模式
class Strategy {
public:
    virtual ~Strategy() = default;
    virtual std::string doAlgorithm(const std::vector<std::string>& data) = 0;
};

class ConcreteStrategyA : public Strategy {
public:
    std::string doAlgorithm(const std::vector<std::string>& data) override {
        std::string result;
        for (const auto& item : data) {
            result += item + ",";
        }
        if (!result.empty()) {
            result.pop_back();  // 移除最后一个逗号
        }
        return result;
    }
};

class ConcreteStrategyB : public Strategy {
public:
    std::string doAlgorithm(const std::vector<std::string>& data) override {
        std::string result;
        for (auto it = data.rbegin(); it != data.rend(); ++it) {
            result += *it + ",";
        }
        if (!result.empty()) {
            result.pop_back();
        }
        return result;
    }
};

class Context {
private:
    std::unique_ptr<Strategy> strategy_;
    
public:
    Context(std::unique_ptr<Strategy> strategy) : strategy_(std::move(strategy)) {}
    
    void setStrategy(std::unique_ptr<Strategy> strategy) {
        strategy_ = std::move(strategy);
    }
    
    std::string doSomeBusinessLogic() {
        std::vector<std::string> data = {"a", "b", "c", "d", "e"};
        std::string result = strategy_->doAlgorithm(data);
        return "Context: 使用策略排序数据 " + result;
    }
};

// 命令模式
class Command {
public:
    virtual ~Command() = default;
    virtual void execute() = 0;
};

class Receiver {
public:
    void doSomething(const std::string& a) {
        std::cout << "Receiver: 工作中 (" << a << ")" << std::endl;
    }
    
    void doSomethingElse(const std::string& b) {
        std::cout << "Receiver: 同时工作中 (" << b << ")" << std::endl;
    }
};

class SimpleCommand : public Command {
private:
    std::string payload_;
    
public:
    explicit SimpleCommand(const std::string& payload) : payload_(payload) {}
    
    void execute() override {
        std::cout << "SimpleCommand: 简单事情 (" << payload_ << ")" << std::endl;
    }
};

class ComplexCommand : public Command {
private:
    Receiver* receiver_;
    std::string a_;
    std::string b_;
    
public:
    ComplexCommand(Receiver* receiver, const std::string& a, const std::string& b)
        : receiver_(receiver), a_(a), b_(b) {}
    
    void execute() override {
        std::cout << "ComplexCommand: 复杂事情由接收者对象完成" << std::endl;
        receiver_->doSomething(a_);
        receiver_->doSomethingElse(b_);
    }
};

class Invoker {
private:
    std::unique_ptr<Command> on_start_;
    std::unique_ptr<Command> on_finish_;
    
public:
    void setOnStart(std::unique_ptr<Command> command) {
        on_start_ = std::move(command);
    }
    
    void setOnFinish(std::unique_ptr<Command> command) {
        on_finish_ = std::move(command);
    }
    
    void doSomethingImportant() {
        std::cout << "Invoker: 开始之前有人想做什么?" << std::endl;
        if (on_start_) {
            on_start_->execute();
        }
        
        std::cout << "Invoker: ...做一些重要的事情..." << std::endl;
        
        std::cout << "Invoker: 完成后有人想做什么?" << std::endl;
        if (on_finish_) {
            on_finish_->execute();
        }
    }
};

🔄 模板方法模式

算法骨架

cpp
#include <iostream>
#include <string>

class AbstractClass {
public:
    // 模板方法定义算法骨架
    void templateMethod() {
        baseOperation1();
        requiredOperation1();
        baseOperation2();
        hook1();
        requiredOperation2();
        baseOperation3();
        hook2();
    }
    
protected:
    // 基础操作已经实现
    void baseOperation1() {
        std::cout << "AbstractClass: 我正在做大部分工作" << std::endl;
    }
    
    void baseOperation2() {
        std::cout << "AbstractClass: 但我让子类重写一些操作" << std::endl;
    }
    
    void baseOperation3() {
        std::cout << "AbstractClass: 但我还是在做大部分工作" << std::endl;
    }
    
    // 抽象操作必须在子类中实现
    virtual void requiredOperation1() = 0;
    virtual void requiredOperation2() = 0;
    
    // 钩子方法有默认实现,但可以被重写
    virtual void hook1() {}
    virtual void hook2() {}
};

class ConcreteClass1 : public AbstractClass {
protected:
    void requiredOperation1() override {
        std::cout << "ConcreteClass1: 实现操作1" << std::endl;
    }
    
    void requiredOperation2() override {
        std::cout << "ConcreteClass1: 实现操作2" << std::endl;
    }
};

class ConcreteClass2 : public AbstractClass {
protected:
    void requiredOperation1() override {
        std::cout << "ConcreteClass2: 实现操作1" << std::endl;
    }
    
    void requiredOperation2() override {
        std::cout << "ConcreteClass2: 实现操作2" << std::endl;
    }
    
    void hook1() override {
        std::cout << "ConcreteClass2: 重写hook1" << std::endl;
    }
};

// 状态模式
class Context;

class State {
public:
    virtual ~State() = default;
    virtual void handle1(Context* context) = 0;
    virtual void handle2(Context* context) = 0;
};

class Context {
private:
    std::unique_ptr<State> state_;
    
public:
    Context(std::unique_ptr<State> state) : state_(std::move(state)) {}
    
    void transitionTo(std::unique_ptr<State> state) {
        std::cout << "Context: 转换状态" << std::endl;
        state_ = std::move(state);
    }
    
    void request1() {
        state_->handle1(this);
    }
    
    void request2() {
        state_->handle2(this);
    }
};

class ConcreteStateA : public State {
public:
    void handle1(Context* context) override;
    void handle2(Context* context) override {
        std::cout << "ConcreteStateA 处理请求2" << std::endl;
    }
};

class ConcreteStateB : public State {
public:
    void handle1(Context* context) override {
        std::cout << "ConcreteStateB 处理请求1" << std::endl;
    }
    
    void handle2(Context* context) override;
};

void ConcreteStateA::handle1(Context* context) {
    std::cout << "ConcreteStateA 处理请求1" << std::endl;
    std::cout << "ConcreteStateA 想要改变上下文的状态" << std::endl;
    context->transitionTo(std::make_unique<ConcreteStateB>());
}

void ConcreteStateB::handle2(Context* context) {
    std::cout << "ConcreteStateB 处理请求2" << std::endl;
    std::cout << "ConcreteStateB 想要改变上下文的状态" << std::endl;
    context->transitionTo(std::make_unique<ConcreteStateA>());
}

// 设计模式演示
class DesignPatternDemo {
public:
    static void singletonDemo() {
        std::cout << "=== 单例模式演示 ===" << std::endl;
        
        auto* s1 = Singleton::getInstance();
        auto* s2 = Singleton::getInstance();
        
        std::cout << "同一个实例? " << (s1 == s2 ? "是" : "否") << std::endl;
        
        s1->doSomething();
        
        auto& es1 = EagerSingleton::getInstance();
        auto& es2 = EagerSingleton::getInstance();
        
        std::cout << "饿汉式同一个实例? " << (&es1 == &es2 ? "是" : "否") << std::endl;
    }
    
    static void factoryDemo() {
        std::cout << "\n=== 工厂方法演示 ===" << std::endl;
        
        auto creatorA = std::make_unique<ConcreteCreatorA>();
        auto creatorB = std::make_unique<ConcreteCreatorB>();
        
        creatorA->someOperation();
        creatorB->someOperation();
    }
    
    static void builderDemo() {
        std::cout << "\n=== 建造者模式演示 ===" << std::endl;
        
        Director director;
        ConcreteHouseBuilder builder;
        
        auto house = director.construct(builder);
        house->show();
    }
    
    static void adapterDemo() {
        std::cout << "\n=== 适配器模式演示 ===" << std::endl;
        
        auto adaptee = std::make_unique<Adaptee>();
        auto adapter = std::make_unique<Adapter>(std::move(adaptee));
        
        std::cout << adapter->request() << std::endl;
    }
    
    static void decoratorDemo() {
        std::cout << "\n=== 装饰器模式演示 ===" << std::endl;
        
        auto component = std::make_unique<ConcreteComponent>();
        std::cout << "客户端: 我有一个简单组件:" << std::endl;
        std::cout << component->operation() << std::endl;
        
        auto decorator1 = std::make_unique<ConcreteDecoratorA>(std::move(component));
        auto decorator2 = std::make_unique<ConcreteDecoratorB>(std::move(decorator1));
        
        std::cout << "客户端: 现在我有一个装饰组件:" << std::endl;
        std::cout << decorator2->operation() << std::endl;
    }
    
    static void observerDemo() {
        std::cout << "\n=== 观察者模式演示 ===" << std::endl;
        
        Subject subject;
        ConcreteObserver observer1("观察者1");
        ConcreteObserver observer2("观察者2");
        
        subject.attach(&observer1);
        subject.attach(&observer2);
        
        subject.setState("第一个状态");
        subject.setState("第二个状态");
        
        subject.detach(&observer1);
        subject.setState("第三个状态");
    }
    
    static void strategyDemo() {
        std::cout << "\n=== 策略模式演示 ===" << std::endl;
        
        Context context(std::make_unique<ConcreteStrategyA>());
        std::cout << context.doSomeBusinessLogic() << std::endl;
        
        context.setStrategy(std::make_unique<ConcreteStrategyB>());
        std::cout << context.doSomeBusinessLogic() << std::endl;
    }
    
    static void commandDemo() {
        std::cout << "\n=== 命令模式演示 ===" << std::endl;
        
        Invoker invoker;
        invoker.setOnStart(std::make_unique<SimpleCommand>("Say Hi!"));
        
        Receiver receiver;
        invoker.setOnFinish(std::make_unique<ComplexCommand>(&receiver, "发送邮件", "保存报告"));
        
        invoker.doSomethingImportant();
    }
    
    static void templateMethodDemo() {
        std::cout << "\n=== 模板方法演示 ===" << std::endl;
        
        std::cout << "同样的客户端代码可以与不同的子类一起工作:" << std::endl;
        
        ConcreteClass1 class1;
        class1.templateMethod();
        
        std::cout << std::endl;
        
        ConcreteClass2 class2;
        class2.templateMethod();
    }
    
    static void stateDemo() {
        std::cout << "\n=== 状态模式演示 ===" << std::endl;
        
        Context context(std::make_unique<ConcreteStateA>());
        context.request1();
        context.request2();
    }
};

int main() {
    DesignPatternDemo::singletonDemo();
    DesignPatternDemo::factoryDemo();
    DesignPatternDemo::builderDemo();
    DesignPatternDemo::adapterDemo();
    DesignPatternDemo::decoratorDemo();
    DesignPatternDemo::observerDemo();
    DesignPatternDemo::strategyDemo();
    DesignPatternDemo::commandDemo();
    DesignPatternDemo::templateMethodDemo();
    DesignPatternDemo::stateDemo();
    
    return 0;
}

总结

设计模式提供了经过验证的解决方案,帮助解决常见的设计问题:

模式分类

  • 创建型模式: 对象创建机制
  • 结构型模式: 对象组合方式
  • 行为型模式: 对象间通信

常用模式

模式用途适用场景
单例确保唯一实例配置管理、日志
工厂创建对象产品族创建
观察者事件通知GUI、MVC架构
策略算法选择行为变化
装饰器动态添加功能功能扩展

设计原则

  • 单一职责: 一个类只负责一个功能
  • 开闭原则: 对扩展开放,对修改关闭
  • 里氏替换: 子类可以替换父类
  • 接口隔离: 接口应该小而专一
  • 依赖倒置: 依赖抽象而非具体

最佳实践

  • 根据实际需要选择模式
  • 避免过度设计
  • 结合SOLID原则使用
  • 考虑性能影响
  • 保持代码简洁

C++特色

  • 利用RAII管理资源
  • 使用智能指针自动管理内存
  • 模板和泛型编程
  • 移动语义优化性能

设计模式是软件设计的重要工具,但应该在合适的场景下谨慎使用,避免为了使用模式而使用模式。

本站内容仅供学习和研究使用。