среда, 21 августа 2013 г.

template-template parameters

template-template parameters
/** Шаблонные шаблонные параметры это прошлый век, они не удобны. Я
    постараюсь объяснить как их избежать. Есть класс A, в котором
    нужно объявлять контейнер из произвольного типа, а тип контейнера
    передавать параметром шаблона: */
template <typename T, typename Container>
struct A
{
  typedef Container<T> type;
};

/** Но так как Container это шаблон, принимающий два параметра: тип
    данных и тип аллокатора, то следует писать так: */

template <typename T, template<typename, typename> class Container>
struct A
{
  typedef Container<T, std::allocator<T> > type;
}

/** Это плохо, я не хочу указывать явно и самостоятельно тип
    аллокатора, это может првести к ошибке.  Ещё одна из причин,
    почему шаблонные шаблонные параметры неудобны.  Чтобы получить тип
    теперь мы должны вызвать: */
typedef A<int, std::vector>::type type;

/** В boost mpl есть плейсхолдеры, которые используются для создания
    лямбда метафункций.  Так вот, с помощью них можно избежать
    создания шаблонных шаблонных параметров.  То есть я передаю в
    шаблон A уже инстанцированный шаблон так: */
typedef A<int, std::vector<boost::mpl::_1> >::type type;

/** Тогда в шаблоне A инстанцирование конейнера с произвольным типом
    будет выглядеть так: */

#include <boost/mpl/apply.hpp>

template <typename T, typename Container>
struct A
{
  typedef typename boost::mpl::apply<Container, T>::type type;
};

1 комментарий: