仅适用于基本POD的模板专业化

时间:2012-01-14 17:30:55

标签: c++ templates template-specialization pod

模板专业化是否有一个微妙的技巧,以便我可以将一个专门化应用于basic POD(当我说基本的POD我不特别想要结构POD(但我会采用它)。)

template<typename T>
struct DoStuff
{
    void operator()() { std::cout << "Generic\n";}
};
template<>
struct DoStuff</*SOme Magic*/>
{
    void operator()() { std::cout << "POD Type\n";}
};

或者我是否必须为每种内置类型编写特化?

template<typename T>
struct DoStuff
{
    void operator()() { std::cout << "Generic\n";}
};


// Repeat the following template for each of
// unsigned long long, unsigned long, unsigned int, unsigned short, unsigned char
//          long long,          long,          int,          short, signed   char
// long double, double, float, bool
// Did I forget anything?
//
// Is char covered by unsigned/signed char or do I need a specialization for that?
template<>  
struct DoStuff<int>
{
    void operator()() { std::cout << "POD Type\n";}
};

单元测试。

int main()
{
    DoStuff<int>           intStuff;
    intStuff();            // Print POD Type


    DoStuff<std::string>   strStuff;
    strStuff();            // Print Generic
}

3 个答案:

答案 0 :(得分:6)

如果您真的只想要基本类型而不是用户定义的POD类型,那么以下内容应该有效:

#include <iostream>
#include <boost/type_traits/integral_constant.hpp>
#include <boost/type_traits/is_fundamental.hpp>
#include <boost/type_traits/is_same.hpp>

template<typename T>
struct non_void_fundamental : boost::integral_constant<
    bool,
    boost::is_fundamental<T>::value && !boost::is_same<T, void>::value
>
{ };

template<typename T, bool Enable = non_void_fundamental<T>::value>
struct DoStuff
{
    void operator ()() { std::cout << "Generic\n"; } const
};

template<>
struct DoStuff<T, true>
{
    void operator ()() { std::cout << "POD Type\n"; } const
};

如果您还想要用户定义的POD类型,那么请使用boost::is_pod<>而不是non_void_fundamental<>(如果您使用C ++ 11并执行此操作以进行优化,请使用{{1}而不是)。

答案 1 :(得分:6)

在C ++ 11中,标准库中添加了许多特征,大多数特征似乎特别针对有趣的特化(尤其是按位操作)。

您可能感兴趣的顶级特征是std::is_trivial,但还有很多其他特性:

  • std::is_trivially_default_constructible
  • std::is_trivially_copy_constructible
  • std::is_trivially_move_constructible
  • std::is_trivially_copyable(可以通过memcpy复制)

一般来说,标准试图尽可能地获得更细粒度的特征,因此您不必依赖is_pod这样的广泛假设,而是微调您的约束以匹配您的方法真正需要的。

答案 2 :(得分:1)

Boost有boost::is_pod。这就是你要找的东西吗?

(我从来没有使用它,所以我不会因为试图为你的例子制定你需要的精确代码而使自己难堪。)