c++ 设计模式之CRTP

CRTP(Curiously Recurring Template Pattern,奇异递归模板模式)是 C++ 中一种常见的静态多态实现技术,也是很多高性能库(如 Eigen、Boost、LLVM)中的核心设计模式之一。


💡 CRTP 本质定义

CRTP 是一种用子类作为模板参数传递给父类的技术。

📌 基本语法:

cpp 复制代码
template <typename Derived>
class Base {
public:
    void interface() {
        // 调用派生类实现的方法
        static_cast<Derived*>(this)->implementation();
    }

    // 可选默认实现
    void implementation() {
        std::cout << "Base implementation\n";
    }
};

class Derived : public Base<Derived> {
public:
    void implementation() {
        std::cout << "Derived implementation\n";
    }
};

调用方式:

cpp 复制代码
int main() {
    Derived d;
    d.interface();  // 输出:Derived implementation
}

✅ CRTP 的主要用途

1. 实现静态多态(Static Polymorphism)

  • 替代虚函数机制,避免运行时开销(如 vtable、动态绑定等)。

2. 代码复用

  • 基类可以定义通用接口逻辑,细节延迟到派生类实现。

3. 在编译期做优化

  • 比如 Eigen 库使用 CRTP 编写矩阵类,实现表达式模板,从而避免中间对象、提升性能。

🧠 CRTP 与虚函数的对比

特性 虚函数(动态多态) CRTP(静态多态)
多态绑定 运行时 编译期
开销 有虚表开销 零开销
灵活性 更高 限制派生结构
可扩展性 较低
使用场景 插件式架构、通用接口 高性能场景、模板库

📦 典型应用案例

1. 编写通用操作接口

cpp 复制代码
template <typename Derived>
class Shape {
public:
    void draw() {
        static_cast<Derived*>(this)->drawImpl();
    }
};

class Circle : public Shape<Circle> {
public:
    void drawImpl() {
        std::cout << "Drawing Circle\n";
    }
};

class Square : public Shape<Square> {
public:
    void drawImpl() {
        std::cout << "Drawing Square\n";
    }
};

2. 实现计数器(统计子类个数)

cpp 复制代码
template <typename T>
class Counter {
public:
    Counter() { ++count; }
    static int count;
};

template <typename T>
int Counter<T>::count = 0;

class MyClassA : public Counter<MyClassA> {};
class MyClassB : public Counter<MyClassB> {};

🔍 高级话题

与策略模式结合

cpp 复制代码
template <typename Derived>
class Sorter {
public:
    void sort() {
        static_cast<Derived*>(this)->doSort();
    }
};

class QuickSorter : public Sorter<QuickSorter> {
public:
    void doSort() {
        std::cout << "Quick Sort\n";
    }
};

表达式模板(如 Eigen)

Eigen 用 CRTP 实现表达式模板,以支持像 C = A + B 这样的操作不会生成临时变量,而是按需展开计算。


🧩 总结

项目 说明
类型 模板设计模式
优势 静态多态、零开销
缺点 结构固定、调试复杂
典型使用 Eigen、Boost、LLVM

ps:Eigen 是一个 高性能 C++ 线性代数库,广泛用于矩阵运算、向量计算、数值解法等领域。许多著名的框架都使用它作为矩阵运算库。例如TensorFlow,OpenCV等。

相关推荐
REDcker2 小时前
有限状态机与状态模式详解 FSM建模Java状态模式与C++表驱动模板实践
java·c++·状态模式
basketball6163 小时前
C++ 构造函数完全指南:从入门到进阶
java·开发语言·c++
想唱rap4 小时前
IO多路转接之poll
服务器·开发语言·数据库·c++
落羽的落羽5 小时前
【算法札记】练习 | Week4
linux·服务器·数据结构·c++·人工智能·算法·动态规划
goodesocket5 小时前
芯片HAST测试:通电工作下如何精准模拟极端环境挑战?
c++
特种加菲猫6 小时前
从零开始手撕AVL树:详解插入、平衡因子更新与四种旋转
开发语言·c++
萑澈6 小时前
算法竞赛入门:C++ STL核心用法与时空复杂度速查手册
数据结构·c++·算法·stl
江屿风6 小时前
C++OJ题经验总结(竞赛)1
开发语言·c++·笔记·算法
运筹vivo@7 小时前
LeetCode 2405. 子字符串的最优划分
c++·算法·leetcode·职场和发展·哈希表
有点。7 小时前
C++(枚举法一练习题)
开发语言·c++·算法