c++ - 通过 CRTP 使用派生类变量初始化基类静态常量变量

标签 c++ templates

以下程序可以在 Cygwin GCC 4.8.2 中编译和运行,但不能在 MSCV 2008(或 MSVC 2013)中编译和运行

#include <iostream>

template<typename T>
struct Base
{
    static const unsigned BAR = T::FOO;

    static void func()
    {
        std::cout << BAR << std::endl;
    }
};

template<typename T>
struct Derived : Base<Derived<T> >
{
    static const unsigned FOO = 42;
};

int main()
{   
    Derived<int>::func();
}

MSVC 错误

Test.cpp(6) : error C2039: 'FOO' : is not a member of 'Derived<T>'
        with
        [
            T=int
        ]
        Test.cpp(16) : see reference to class template instantiation 'Base<T>' being compiled
        with
        [
            T=Derived<int>
        ]
        Test.cpp(24) : see reference to class template instantiation 'Derived<T>' being compiled
        with
        [
            T=int
        ]
Test.cpp(6) : error C2065: 'FOO' : undeclared identifier
Test.cpp(6) : error C2057: expected constant expression

此程序是否合规或这是一个 MSCV 问题?另外,有解决方法吗?

最佳答案

编辑 2:在派生类声明后拒绝初始化就足够了。

我可以让 MSVC 和 Clang 编译您的程序的唯一方法是:

  • 在派生类声明后拒绝 Base::BAR 初始化
  • 使用Derived的具体实现来初始化BAR

编辑:我认为这是正常的,因为在您的代码中,编译器没有意义在编译 Base 时 知道 T::FOO 将存在并且将是一个常量值。

当前来源是:

#include <iostream>

template<typename T>
struct Base
{
    static const unsigned BAR;

    static void func()
    {
        std::cout << BAR << std::endl;
    }
};

template<typename T>
struct Derived : Base<Derived<T> >
{
    static const unsigned FOO = 42;
};

template<typename T>
const unsigned Base<T>::BAR = T::FOO;

int main()
{   
    Derived<int>::func();
}

关于c++ - 通过 CRTP 使用派生类变量初始化基类静态常量变量,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/27443063/

相关文章:

c++ - 等待多个对象发出信号

templates - 有没有办法使用 mixin 或模板从 D 中的类生成接口(interface)?

c++ - 即使在函数退出后也保持 ofstream 对象打开

java - 将对象移动到椭圆的边缘

c++ - CUDA:二维网格中的线程 ID 分配

templates - chalice : Writing a taglib which uses a template to render data and keep it controller agnostic

c++ - GCC Shared_ptr 模板错误

c++ - 可变参数模板特化问题

c++ - 试图用模板编译嵌套类?

c++ - 诊断多重定义错误