2

已经提出了许多问题,它们与我在这里要问的问题相似,但我认为它们并不相同。

我有一个模板类:

namespace app {
template <typename T>
class MyCLass {
public:
  void dosome();
  void doother();
}
} /*ns*/

和实现:

template <typename T>
app::MyClass<T>::dosome() {}
template <typename T>
app::MyClass<T>::doother() {}

当我有一个char作为模板参数提供的类的实例时,我希望函数dosome()以完全不同的方式运行。但我只是希望该功能表现不同,其他一切都必须保持相同。

我试着输入:

template<>
app::MyCLass<char>::dosome() {
}

但是编译器告诉我我正在尝试在不同的命名空间中创建一个专业化。

所以当我有这样的代码时:

app::MyCLass<int> a;
app::MyCLass<char> b;
a.dosome(); // This must call the generic template definition
b.dosome(); // This must call the specialization
a.doother(); // This must call the generic template definition
b.doother(); // This must call the generic template definition

在其他问题中,我看到人们为整个班级创造了完全不同的专业。但我只想要一种方法的专业化。

4

2 回答 2

2

一种选择是标签调度:

template <typename T>
class MyClass {
public:
  void dosome() { dosome_impl( T() ); }

private:

  void dosome_impl(char) { /* char stuff */ }  
  template<typename U>
  void dosome_impl(U) { /* usual stuff */ }
};

另一种是enable_if成语:

#include <type_traits>

template <typename T>
class MyClass {
public:
  template<typename U = T>
  typename std::enable_if<std::is_same<U,char>::value>::type
  dosome() { /* char stuff */ }

  template<typename U = T>
  typename std::enable_if<!std::is_same<U,char>::value>::type
  dosome() { /* normal stuff */ }
};

还有一个是将单个函数移动到您可以专门化的基类:

template <typename T>
struct MyClass_base {
    dosome() { /* usual stuff */ }
};

template<>
struct MyClass_base<char> {
    dosome() { /* char stuff */ } 
};

template <typename T>
class MyClass : private MyClass_Base<T> {
public:
    // nothing special here
};
于 2013-09-09T15:33:18.650 回答
2

你可以做你想做的事:http: //ideone.com/oKTFPC

// 标题

namespace My
{

template <typename T>
class MyClass {
public:
    void dosome();
    void doother();
};

template <typename T> void MyClass<T>::dosome() {}
template <typename T> void MyClass<T>::doother() {}

template<> void MyClass<char>::dosome();

}

// cpp 或在标头中

template<>
void My::MyClass<char>::dosome() {
    std::cout << "specialization" << std::endl;
}

或使用替代符号

namespace My {
template<>
void MyClass<char>::dosome() {
    std::cout << "specialization" << std::endl;
}
}
于 2013-09-09T16:01:45.390 回答