C++ - Template Specialization & Partial Specialization

谁都会走 提交于 2019-12-03 16:25:12

It seems you want to define only some functions of some specializations : if print() does not change between the char specialization and the general case, it seems that you don't want to redefine it.

// What you want to do (illegal in C++)
template<int,typename T>
struct Z
{
    T myValue;
    Z();
    void print() { /* ... */ }
};

template<int i, typename T>
Z<i,T>::Z() { /* ... */ }

template<int i>
Z<i,char>::Z() { /* ... */ }

However, it does not work like this. Partial or full specializations of class have almost nothing in common, except 'prototype' of template parameters:

// The two following types have only two things related: the template parameter is an int,
// and the second type is a full specialization of the first. There are no relations between
// the content of these 2 types.
template<int> struct A {};
template<> struct A<42> { void work(); };

You have to declare and define each (partial) specialization:

// Fixed example
template<int,typename T>
struct Z
{
    T myValue;
    Z();
    void print() { /* ... */ }
};
template<int i, typename T>
Z<i,T>::Z() { /* ... */ }

// Specialization for <all-ints,char>
template<int i>
struct Z<i,char>
{
    char myValue;
    char othervalue;
    Z();
    void print() { /* Same code than for the general case */ }
};

template<int i>
Z<i,char>::Z() { /* ... */ }

The only way to escape the code duplication is by using inheritance of traits:

// Example with the print function
template<typename T>
struct print_helper
{
    void print() { /* ... */ }
};

// Fixed example
template<int,typename T>
struct Z : public print_helper<T>
{
    T myValue;
    Z();
};
template<int i, typename T>
Z<i,T>::Z() { /* ... */ }

// Specialization for <all-ints,char>
template<int i>
struct Z<i,char> : public print_helper<char>
{
    char myValue;
    char othervalue;
    Z();
};

template<int i>
Z<i,char>::Z() { /* ... */ }

You cannot do what you want without duplication for the moment (the feature removing code duplication is static if and has been proposed for the next C++ standard, see n3322 and n3329).

You may have a look at this course http://channel9.msdn.com/Series/C9-Lectures-Stephan-T-Lavavej-Core-C-/Stephan-T-Lavavej-Core-C-5-of-n

While this is not possible that you define partial specialization for function templates, you can define partial specialization for class or struct template.

template<typename T> struct helper {
    static void doThingy(){}
};

template<typename X> struct helper<X*> {
    static void doThingy(){}
};

Helper(double*)::doThingy();

In this example, you want to specialize behavior in doThingy() only when the type in template is a pointer type. You cannot use overload of method doThingy() in this case. This is because you cannot overload a function with no arguments. But you can have partial specialization of the struct helper. In specialized template, you implemented wished behavior for the doThingy().

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!