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

Template Specialization for basic POD only

本文关键字:POD 适用于 专业化      更新时间:2023-10-16

模板专门化有没有一个微妙的技巧,这样我就可以对basic POD应用一个专门化(当我说基本POD时,我并不特别想要结构POD(但我会接受))。

template<typename T>
struct DoStuff
{
    void operator()() { std::cout << "Genericn";}
};
template<>
struct DoStuff</*SOme Magic*/>
{
    void operator()() { std::cout << "POD Typen";}
};

或者我必须为每种内置类型编写专门化?

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

// 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 Typen";}
};

单元测试。

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

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

如果您真的只想要基本类型而不想要用户定义的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 << "Genericn"; } const
};
template<>
struct DoStuff<T, true>
{
    void operator ()() { std::cout << "POD Typen"; } const
};

如果您还想要用户定义的POD类型,请使用boost::is_pod<>而不是non_void_fundamental<>(如果您使用C++11并出于优化目的这样做,请改用std::is_trivially_copyable<>)。

在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这样广泛的假设,而是对约束进行微调,以匹配您的方法真正需要的内容。

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

(我从未使用过它,所以我不会因为试图为您的示例制定所需的精确代码而让自己感到尴尬。)