模板专业化和静态成员初始化

时间:2019-01-19 15:17:02

标签: c++ c++11 templates specialization

我们说有一个模板化的类:

template<typename T>
class Storage
{
public:
    static std::map<T, std::vector<std::string> > things;
};

现在我想将其专门用于类型int并初始化things

到目前为止我发现的不会引发编译错误的方式是:

template<>
std::map<int, std::vector<std::string> > Storage<int>::things = {
    { 1, {"FOO", "foo"} },
    { 2, {"BAR", "bar"} },
    { 3, {"ZAR", "zar"} }
};

但是事实证明,我们可以专门化类并同时初始化静态成员吗​​?

1 个答案:

答案 0 :(得分:0)

代码:

template<>
std::map<int, std::vector<std::string> > Storage<int>::things = {
    { 1, {"FOO", "foo"} },
    { 2, {"BAR", "bar"} },
    { 3, {"ZAR", "zar"} }
};

不是类模板Storage的专业化,而是a static data member of a class template的专业化。

模板类的成员可以专用(只要没有非静态数据成员)。也就是说,可以将整个模板类作为一个整体专门化:

template<class T>
struct A{
   struct B{
      using type = T;
      };
    void g();
    };

 template<>
 struct A<void>{}; //specialize the entire class.

或仅将类模板的成员专门化:

//Specialization of B for A<int>
template<>
struct A<int>::B{
   static int f();
   };

以上成员专业化等同于模板类专业化:

template<>
struct A<int>{
   struct B{ //come from the member specialization definition
     static int f();
     };
   void g(); //come from unspecialized A definition.
   };

因此,如果尝试编译,则可能会观察到此情况:

A<char>::B::type x = `a`; 
A<double>::B::type y = `b`; 

A<int>::B::type err; //compilation error
int z = A<int>::B::f(); //ok.

A<void>::B o; //compilation error
auto w = A<void>::f(); //compilation error