2012-10-13 20 views
6

Załóżmy, że mam następujące klasy:Specjalizacja metody klasy szablon

template <typename T> 
class MyClass 
{ 
public: 
    void SetValue(const T &value) { m_value = value; } 

private: 
    T m_value; 
}; 

Jak mogę napisać wyspecjalizowaną wersję funkcji, dla t = float (lub innego typu)?

Uwaga: Proste przeciążenie nie wystarczy, ponieważ chcę tylko, aby funkcja była dostępna dla T = float (tj. MyClass :: SetValue (float) w tym przypadku nie ma sensu).

Odpowiedz

8
template <typename T> 
class MyClass { 
private: 
    T m_value; 

private: 
    template<typename U> 
    void doSetValue (const U & value) { 
     std::cout << "template called" << std::endl; 
     m_value = value; 
    } 

    void doSetValue (float value) { 
     std::cout << "float called" << std::endl; 
    } 

public: 
    void SetValue(const T &value) { doSetValue (value); } 

}; 

lub (częściowa specjalizacja szablonu):

template <typename T> 
class MyClass 
{ 
private: 
    T m_value; 

public: 
    void SetValue(const T &value); 

}; 

template<typename T> 
void MyClass<T>::SetValue (const T & value) { 
    std::cout << "template called" << std::endl; 
    m_value = value; 
} 

template<> 
void MyClass<float>::SetValue (const float & value) { 
    std::cout << "float called" << std::endl; 
} 

lub, jeśli chcesz funkcje mają różne podpisy

template<typename T> 
class Helper { 
protected: 
    T m_value; 
    ~Helper() { } 

public: 
    void SetValue(const T &value) { 
     std::cout << "template called" << std::endl; 
     m_value = value; 
    } 
}; 

template<> 
class Helper<float> { 
protected: 
    float m_value; 
    ~Helper() { } 

public: 
    void SetValue(float value) { 
     std::cout << "float called" << std::endl; 
    } 
}; 

template <typename T> 
class MyClass : public Helper<T> { 
}; 
+0

Twoja częściowa odpowiedź na szablon specjalizacji trafia w sedno! Właśnie tego szukałem, dzięki. –

+0

W drugim przykładzie jest to wyraźna specjalizacja szablonów: Zapewniasz wszystkie 1 z 1 argumentów (szablonów) szablonu, gdyby były, musiałbyś dostarczyć 2. Kolejną kwestią jest, że te wyspecjalizowane funkcje najwyraźniej muszą znajdować się w oddzielnej jednostce kompilacji (nie w pliku nagłówkowym), jeśli umieścisz szablon w pliku nagłówkowym i umieścisz go dwukrotnie. – Markus

2

Pewnie, że możesz. Tyle, że powinien to być przeciążenie :)

template <typename T> 
class MyClass 
{ 
public: 
    template<class U> 
    void SetValue(const U &value) { m_value = value; } 
    void SetValue(float value) {do special stuff} 
private: 
    T m_value; 
}; 

int main() 
{ 
    MyClass<int> mc; 
    mc.SetValue(3.4); // the template member with U=double will be called 
    mc.SetValue(3.4f); // the special function that takes float will be called 

    MyClass<float> mcf; //compiles OK. If the SetValue were not a template, 
    // this would result in redefinition (because the two SetValue functions 
    // would be the same 
} 
+2

Ale chcę, aby przeciążenie pływaka było dostępne, gdy T = float. W przeciwnym razie możesz mieć 'MyClass :: SetValue (float)', które nie ma żadnego sensu. –

Powiązane problemy