C++ 设计模式-组合模式

组合模式(Composite Pattern)允许将对象组合成树形结构,使得客户端以统一的方式处理单个对象和组合对象。以下是一个经典的 C++ 实现示例,包含透明式设计(基类定义统一接口)和内存管理:

cpp 复制代码
#include <iostream>
#include <vector>
#include <algorithm>
#include <stdexcept>
#include <memory>

// 抽象组件类
class Component {
public:
    virtual ~Component() = default;
    virtual void operation() const = 0;
    
    // 管理子组件的透明接口(Leaf需处理不支持的操作)
    virtual void add(std::unique_ptr<Component> component) {
        throw std::runtime_error("Unsupported operation: add");
    }
    virtual void remove(Component* component) {
        throw std::runtime_error("Unsupported operation: remove");
    }
    virtual const Component* getChild(int index) const {
        throw std::runtime_error("Unsupported operation: getChild");
    }
};

// 叶子节点类
class Leaf : public Component {
public:
    explicit Leaf(std::string name) : name_(std::move(name)) {}
    
    void operation() const override {
        std::cout << "Leaf[" << name_ << "] 执行操作" << std::endl;
    }
    
private:
    std::string name_;
};

// 组合节点类
class Composite : public Component {
public:
    void operation() const override {
        std::cout << "Composite 执行操作,包含" << children_.size() << "个子组件:" << std::endl;
        for (const auto& child : children_) {
            child->operation(); // 递归调用子组件的操作
        }
    }
    
    void add(std::unique_ptr<Component> component) override {
        children_.push_back(std::move(component));
    }
    
    void remove(Component* component) override {
        auto it = std::find_if(children_.begin(), children_.end(),
            [component](const std::unique_ptr<Component>& c) {
                return c.get() == component;
            });
        if (it != children_.end()) {
            children_.erase(it);
        }
    }
    
    const Component* getChild(int index) const override {
        if (index >= 0 && index < children_.size()) {
            return children_[index].get();
        }
        return nullptr;
    }

private:
    std::vector<std::unique_ptr<Component>> children_; // 使用智能指针管理生命周期
};

// 客户端代码
int main() {
    // 创建组合结构:root -> [branch1, branch2]
    // branch1 -> [leaf1, leaf2]
    // branch2 -> [leaf3]
    auto root = std::make_unique<Composite>();
    
    auto branch1 = std::make_unique<Composite>();
    branch1->add(std::make_unique<Leaf>("A"));
    branch1->add(std::make_unique<Leaf>("B"));
    
    auto branch2 = std::make_unique<Composite>();
    branch2->add(std::make_unique<Leaf>("C"));
    
    root->add(std::move(branch1));
    root->add(std::move(branch2));
    
    // 统一调用操作
    root->operation();
    
    return 0;
}

关键点解析:

  1. 透明式设计

    • Component 基类定义了所有组件(包括叶子节点)的公共接口,包括 add/remove 等管理子组件的方法。
    • 叶子节点 Leaf 继承自 Component,但重写 add/remove 时抛出异常(代码中省略异常以简化,实际可添加)。
    • 组合节点 Composite 实现子组件管理逻辑,并递归调用子组件的 operation()
  2. 内存管理

    • 使用 std::unique_ptr 管理子组件生命周期,确保组合对象析构时自动释放所有子组件。
    • 避免手动 new/delete,减少内存泄漏风险。
  3. 递归结构

    • Compositeoperation() 会遍历所有子组件并调用它们的操作,形成递归处理。

输出结果:

复制代码
Composite 执行操作,包含2个子组件:
Composite 执行操作,包含2个子组件:
Leaf[A] 执行操作
Leaf[B] 执行操作
Composite 执行操作,包含1个子组件:
Leaf[C] 执行操作

此实现展示了组合模式的核心思想:客户端无需区分叶子节点和组合节点 ,统一通过 Component 接口操作,简化了复杂树形结构的处理。

相关推荐
王燕龙(大卫)30 分钟前
递归下降算法
开发语言·c++·算法
郭涤生1 小时前
C++ 完美转发
c++·算法
whoarethenext1 小时前
数据结构堆的c/c++的实现
c语言·数据结构·c++·
2401_858286112 小时前
CD36.【C++ Dev】STL库的string的使用 (下)
开发语言·c++·类和对象·string
強云2 小时前
性能优化-初识(C++)
c++·性能优化
虾球xz3 小时前
游戏引擎学习第263天:添加调试帧滑块
c++·学习·游戏引擎
努力努力再努力wz4 小时前
【c++深入系列】:万字详解vector(附模拟实现的vector源码)
运维·开发语言·c++·c
yxc_inspire4 小时前
基于Qt的app开发第六天
开发语言·c++·qt
ouliten4 小时前
《C++ Templates》:有关const、引用、指针的一些函数模板实参推导的例子
c++
李匠20245 小时前
C++GO语言微服务项目之 go语言基础语法
开发语言·c++·后端·golang