如果我想专门化模板中的一个方法,我该怎么做?

bob*_*obo 27 c++ templates

假设我有一个模板化的类

template <typename T> struct Node
{
    // general method split
    void split()
    {
        // ... actual code here (not empty)
    }
};
Run Code Online (Sandbox Code Playgroud)

需要在Triangle类案例中专门研究这一点

template <>
struct Node <Triangle*>
{
    // specialise the split method
    void split() {}
} ;
Run Code Online (Sandbox Code Playgroud)

但我希望再次改写整个模板!唯一需要改变的是split()方法,仅此而已.

Luc*_*ore 31

您只能在类声明之外为该函数提供特化.

template <typename T> struct Node
{
    // general method split
    void split()
    {
        // implementation here or somewhere else in header
    }
};
Run Code Online (Sandbox Code Playgroud)

//在cpp中声明的函数原型void splitIntNode(Node&node);

template <>
void Node<int>::split()
{
     splitIntNode( this ); // which can be implemented
}

int main(int argc, char* argv[])
{
   Node <char> x;
   x.split(); //will call original method
   Node <int> k;
   k.split(); //will call the method for the int version
}
Run Code Online (Sandbox Code Playgroud)

如果splitIntNode需要访问私有成员,您只需将这些成员传递给函数而不是整个Node.


Pla*_*aHH 6

只需定义一些

template<>
void Node<Triangle*>::split()
{
}
Run Code Online (Sandbox Code Playgroud)

在主模板之后,但在第一次实例化之前.


Jas*_*son 5

您的案例是一个幸运的例子,因为您完全专注于模板.换句话说,只有一个模板参数,对于您希望专门化的函数,您将提供该函数定义的完全专用的实例化.不幸的是,对于部分类模板特化,需要重新实现该类.

例如,这有效:

template<typename T, typename U>
struct Node
{
    void function() { cout << "Non-specialized version" << endl; }
};

template<>
void Node<int, char>::function() { cout << "Specialized version" << endl; }
Run Code Online (Sandbox Code Playgroud)

部分专业版虽然不起作用:

template<typename T, typename U>
struct Node
{
    void function() { cout << "Non-specialized version" << endl; }
};

template<typename U>
void Node<int, U>::function() { cout << "Specialized version" << endl; }
Run Code Online (Sandbox Code Playgroud)

如果您发现自己处于第二种情况中,为了避免不必要的代码重复,您可能想要做的事情是将所有公共元素打包到一个公共基类中,然后放置所有将随之变化的元素派生类中的部分特化.这样您就不需要重复基类中的所有公共代码,只需要重新编写专用派生类的定义.