Namespaces
Variants

Curiously Recurring Template Pattern

From cppreference.net
C++ language
General topics
Flow control
Conditional execution statements
Iteration statements (loops)
Jump statements
Functions
Function declaration
Lambda function expression
inline specifier
Dynamic exception specifications ( until C++17* )
noexcept specifier (C++11)
Exceptions
Namespaces
Types
Specifiers
constexpr (C++11)
consteval (C++20)
constinit (C++20)
Storage duration specifiers
Initialization
Expressions
Alternative representations
Literals
Boolean - Integer - Floating-point
Character - String - nullptr (C++11)
User-defined (C++11)
Utilities
Attributes (C++11)
Types
typedef declaration
Type alias declaration (C++11)
Casts
Memory allocation
Classes
Class-specific function properties
Special member functions
Templates
Miscellaneous

奇异递归模板模式 是一种编程惯用法,其中类 X 派生自类模板 Y ,并接受模板参数 Z ,而 Y 被实例化时使用 Z = X 。例如,

template<class Z>
class Y {};
class X : public Y<X> {};

示例

CRTP可用于实现"编译期多态",当基类暴露接口,而派生类实现该接口时。

#include <cstdio>
#ifndef __cpp_explicit_this_parameter // 传统语法
template <class Derived>
struct Base
{
    void name() { static_cast<Derived*>(this)->impl(); }
protected:
    Base() = default; // 禁止创建Base对象,否则是未定义行为
};
struct D1 : public Base<D1> { void impl() { std::puts("D1::impl()"); } };
struct D2 : public Base<D2> { void impl() { std::puts("D2::impl()"); } };
#else // C++23 推导this语法
struct Base { void name(this auto&& self) { self.impl(); } };
struct D1 : public Base { void impl() { std::puts("D1::impl()"); } };
struct D2 : public Base { void impl() { std::puts("D2::impl()"); } };
#endif
int main()
{
    D1 d1; d1.name();
    D2 d2; d2.name();
}

输出:

D1::impl()
D2::impl()

参见

显式对象成员函数(推导 this (C++23)
允许对象创建指向自身的 shared_ptr
(类模板)
用于定义 view 的辅助类模板,采用 奇异递归模板模式
(类模板)

外部链接

1. 用概念替换CRTP? — Sandor Drago的博客
2. 奇异递归模板模式(CRTP) — Sandor Drago的博客
3. 奇异递归模板模式(CRTP)- 1 — Fluent { C ++ }
4. CRTP能为代码带来什么 - 2 — Fluent { C ++ }
5. CRTP的实现辅助工具 - 3 — Fluent { C ++ }
6. 什么是奇异递归模板模式(CRTP) — Stack Overflow