模板特化 - 提供可选模板

时间:2015-01-09 12:40:59

标签: c++ templates

我在模板专业化方面有点蠢蠢欲动。

让我们说我实现了一个可以在不同对象之间进行转换的类。为简单起见,我将在基本类型之间进行转换。

class Converter
{
    public:
       Converter() {};

    template <typename ConvT,
              typename FromT>
    static
    ConvT
    convert(From type);
};


template <typename ConvT,
          typename FromT>
ConvT
Converter::convert(FromT type)
{
   return static_cast<ConvT>(type);
}

template <>
double
Converter::convert<double,int>(int type)
{
  return 22.2;
}

现在我可以做这样的事情

float myFloat = Converter::convert<float>(5);
double myTwentyTwoPointTwo = Converter::convert<double>(42);

我希望能够指定一个可选的模板参数,该参数将成为该类型的容器。

// Retrns a std::vector<dobule> with one element, 22.2.
std::vector<double> myDoubleVec = Converter::convert<double, std::vector>(42);

有没有办法扩展这个类,以便它具有此功能?

编辑:这没关系:

Converter::convert<double, int, std::vector>(42);

2 个答案:

答案 0 :(得分:0)

最简单的方法是直接传递容器类型:

#include <vector>

template<typename C, typename T>
C ConvertAndPutIntoContainer(T t) 
{
    C c;
    c.push_back(static_cast<typename C::value_type>(t));
    return c;    
}

// usage
auto x = ConvertAndPutIntoContainer<std::vector<double>>(23);

答案 1 :(得分:0)

选项#1

用于处理转化的单个主要模板 - 标量或容器:

template <typename T>
using identity = T;

struct Converter
{
    template <typename ConvT,
              template <typename...> class ConT = identity,
              typename FromT>
    static ConT<ConvT> convert(FromT type);
};

template <typename ConvT,
          template <typename...> class ConT,
          typename FromT>
ConT<ConvT> Converter::convert(FromT type)
{
    return ConT<ConvT>{ static_cast<ConvT>(type) };
}

DEMO 1

选项#2

容器的单独重载:

struct Converter
{
    //...

    template <typename ConvT,
              template <typename...> class ConT,
              typename FromT>
    static ConT<ConvT> convert(FromT type);
};

template <typename ConvT,
          template <typename...> class ConT,
          typename FromT>
ConT<ConvT> Converter::convert(FromT type)
{
    return ConT<ConvT>{ static_cast<ConvT>(type) };
}

DEMO 2

选项#3

C ++ 03版本,std::vectorstd::liststd::deque容器的单独重载:

struct Converter
{
    //...

    template <typename ConvT,
              template <typename T, typename A = std::allocator<T> > class ConT,
              typename FromT>
    static ConT<ConvT> convert(FromT type);
};

template <typename ConvT,
          template <typename T, typename A = std::allocator<T> > class ConT,
          typename FromT>
ConT<ConvT> Converter::convert(FromT type)
{
    return ConT<ConvT>(1, static_cast<ConvT>(type));
}

DEMO 3

试验:

std::vector<double> v = Converter::convert<double, std::vector>(42);
double d = Converter::convert<double>(42);