是否可以在专用模板类中访问非类型模板参数的值?

时间:2009-07-22 00:08:03

标签: c++ templates template-specialization

是否可以在专用模板类中访问非类型模板参数的值?

如果我有专门化的模板类:

   template <int major, int minor> struct A {
       void f() { cout << major << endl; }
   }

   template <> struct A<4,0> {
       void f() { cout << ??? << endl; }
   }

我知道上面这种情况很难硬编码值4和0而不是使用变量,但是我有一个更大的类,我是专门的,我希望能够访问这些值。

在A&lt; 4,0&gt;中是否可能。访问majorminor值(4和0)?或者我必须在模板实例化时将它们分配为常量:

   template <> struct A<4,0> {
       static const int major = 4;
       static const int minor = 0;
       ...
   }

4 个答案:

答案 0 :(得分:16)

这种问题可以通过一组单独的“特征”结构来解决。

// A default Traits class has no information
template<class T> struct Traits
{
};

// A convenient way to get the Traits of the type of a given value without
// having to explicitly write out the type
template<typename T> Traits<T> GetTraits(const T&)
{
    return Traits<T>();
}

template <int major, int minor> struct A 
{ 
    void f() 
    { 
        cout << major << endl; 
    }   
};

// Specialisation of the traits for any A<int, int>
template<int N1, int N2> struct Traits<A<N1, N2> >
{
    enum { major = N1, minor = N2 };
};

template <> struct A<4,0> 
{       
    void f() 
    { 
        cout << GetTraits(*this).major << endl; 
    }   
};

答案 1 :(得分:1)

不是你的问题的答案,但你可以枚举它们,即:

enum{
 specialisationMajor=4,
 specialisationMinor=0
};

template <> struct A<specialisationMajor,specialisationMinor> {
    static const int major = specialisationMajor;
    static const int minor = specialisationMinor;
    ...
}

答案 2 :(得分:0)

并不是您问题的真正答案,但以下想法对我有帮助:

#include <iostream>

template <int major, int minor, int= major, int= minor> struct A {
    void f() { std::cout << major << '\n'; }
};

template <int major, int minor> struct A<major, minor, 4, 0> {
    void f() { std::cout << major << ':' << minor << '\n'; }
};

int main()
{
    A<3, 3>().f();
    A<4, 0>().f();
}

答案 3 :(得分:0)

否,您无权访问专门的非类型模板参数。但这是一种在执行f时不再重复自己的方法:

   template <int major, int minor>
   struct f_impl
   {
       void f() { cout << major << endl; }
   };

   template <int major, int minor>
   struct A : public f_impl<major, minor>
   {};

   template <> struct A<4,0> : public f_impl<4,0>
   {};

在此示例中,一个人并没有获得太多收益,因为一个人需要写两次4,0(所以您也可以在自己的cout中第二次写它) OP)。但是,如果您使用模板参数具有更多功能,它将开始获得回报。