首頁
編程語言
C語言|JAVA編程
Python編程
網頁編程
ASP編程|PHP編程
JSP編程
數據庫
MYSQL數據庫|SqlServer數據庫
Oracle數據庫|DB2數據庫
您现在的位置: 程式碼之家 >> 編程語言 >  >> C語言 >> C++ >> 關於C++

C++ CRTP 奇異遞迴模板模式:以靜態多態取代虛函數的效能實測

     編輯:關於C++

核心模式 (CRTP)

template <class Derived>
class Base {
public:
    void interface() { static_cast<Derived*>(this)->implementation(); }
protected:
    Base() = default;
};

class Derived : public Base<Derived> {
    friend class Base<Derived>;
    void implementation() { /* 具體實作 */ }
};
  • Base 模板參數為衍生類別 Derived。
  • static_cast<Derived*>(this) 安全下轉 (編譯期已知型別)。
  • 衍生類別在 implementation 實作具體行為,基類提供通用介面。

靜態 vs 動態多態效能對比

測試環境:Linux x86_64, GCC, 1 億次迴圈調用簡單增減操作。

建置模式虛函數耗時CRTP 耗時加速比
無優化 (-O0)1.04 秒1.63 秒虛函數略快 (CRTP 未內聯)
優化 (-O2/-O3)0.62 秒0.056 秒CRTP 快 11 倍

原因分析

  • 虛函數:間接呼叫 (vtable 查找),編譯器**無法內聯** (動態綁定),優化受限。
  • CRTP:static_cast + 直接呼叫,編譯器**完全內聯**展開,消除呼叫開銷,進一步優化迴圈內部邏輯。
  • 優化開啟時,虛函數仍保留間接跳轉;CRTP 變為純量運算,指令流極短。

適用與不適用場景

現代 C++ 補充

  • C++20 **Concepts** 可約束 Derived 需提供的介面,提前報錯。
  • 配合 final 關鍵字防止進一步繼承破壞靜態綁定假設。
  • 標準庫大量使用 CRTP:std::iterator (C++17 deprecated), std::enable_shared_from_this, boost::intrusive 等。

結語

CRTP 是 C++ **零開銷抽象** 的經典範例。在效能敏感、型別固定的熱路徑中,優先考慮 CRTP 替代虛函數;通用介面、擴充性優先場景仍以虛函數為主。兩者並非互斥,可混合使用 (基類虛函數 + CRTP 葉子類別)。

  1. 上一篇文章:
  2. 下一篇文章:
Copyright © 程式碼之家 All Rights Reserved
場景推薦理由
高頻熱路徑、簡單介面、型別封閉CRTP極致效能、零開銷抽象
動態載入插件、跨 DLL 介面虛函數二進位相容、型別抹除
大型類別體系、多重繼承虛函數CRTP 單一繼承限制、編譯期膨脹
需要運行期切換實作虛函數 / std::functionCRTP 編譯期綁定