2013-03-13 2 views
28

Я новичок в шаблонах, поэтому, возможно, это тривиальная вещь, но я не могу заставить ее работать. Я пытаюсь получить частичную специализацию функции члена класса. Самый короткий код:C++ template part special function member function

template <typename T, int nValue> class Object{ 
private: 
    T m_t; 
    Object(); 
public: 
    Object(T t): m_t(t) {} 
    T Get() { return m_t; } 
    Object& Deform(){ 
     m_t*=nValue; 
     return *this; 
    } 
}; 

template <typename T> 
Object<T,0>& Object<T,0>::Deform(){ 
    this->m_t = -1; 
    return *this; 
} 

int main(){ 
    Object<int,7> nObj(1); 
    nObj.Deform(); 
    std::cout<<nObj.Get(); 
} 

Я пробовал с функциями, отличными от членов, и все было в порядке. То, что прекрасно работает, - это полная специализация функции-члена.

Но, когда я пытаюсь с частичной спецификацией. функции члена я получаю сообщение об ошибке вида:

PartialSpecification_MemberFu.cpp(17): error: template argument 
list must match the parameter list Object<T,0>& Object<T,0>::Deform(). 

бы признателен за любую помощь :-)

+1

Актуально: http://stackoverflow.com/questions/1501357/template-specialization-of-particular-members –

ответ

30

Вы не можете частично специализировать только одну функцию-член, вы должны частично специализировать весь класс. Следовательно, вам нужно что-то вроде:

template <typename T> 
class Object<T, 0> 
{ 
private: 
    T m_t; 
    Object(); 
public: 
    Object(T t): m_t(t) {} 
    T Get() { return m_t; } 
    Object& Deform() 
    { 
     std::cout << "Spec\n"; 
     m_t = -1; 
     return *this; 
    } 
}; 
18

14.5.5.3.1. Список параметров шаблона члена частичной специализации шаблона шаблона должен соответствовать списку параметров шаблона частичной специализации шаблона класса. Список аргументов шаблона члена частичной специализации шаблона шаблона должен соответствовать списку аргументов шаблона частичной специализации шаблона шаблона.

Иными словами: частично не имеет специализированного элемента без частично специализированного класса.

3

К сожалению, вы не можете частично специализировать функцию-член класса шаблона. Вы можете либо частично специализировать весь класс, либо использовать наследование. Вы также можете использовать оба:

template <typename T, int nValue> 
class Object { 
protected: 
    T m_t; 
public: 
    Object() = delete; 
    Object(T t): m_t(t) {} 
    T Get() { return m_t; } 
    Object& Deform() { 
     m_t *= nValue; 
     return *this; 
    } 
}; 

template <typename T> 
class Object<T,0> : public Object<T,1> { 
public: 
    using Object<T,1>::Object; 

    Object& Deform() { 
     this->m_t = -1; 
     return *this; 
    } 
};