вопрос о шаблонных функциях c ++, принимающих любой тип, если этот тип соответствует хотя бы одному из требований - PullRequest
4 голосов
/ 29 марта 2010

Поскольку я не могу объяснить это очень хорошо, я сразу начну с небольшого примера:

template <class T> void Print(const T& t){t.print1();}
template <class T> void Print(const T& t){t.print2();}

Это не компилируется:
error C2995: 'void Print(const T &)' : function template has already been defined

Итак, как мне создать шаблонную функцию , которая принимает любой тип T, если этот тип имеет print1 член-функцию ИЛИ print2 член-функцию ( нет полиморфизма )?

Ответы [ 2 ]

5 голосов
/ 29 марта 2010

Один из подходов заключается в использовании SFINAE для обнаружения существования функции ( Можно ли написать шаблон для проверки существования функции? , SFINAE для проверки унаследованных функций-членов ) и объединить знания с чем-то вроде Boost.Enable_if .

1 голос
/ 29 марта 2010

@ UncleBens: не хотел редактировать ваше сообщение, вот пример кода (надеюсь, созрел для копирования / вставки), поместите его в свой пост и прокомментируйте этот ответ, чтобы я мог удалить его:)

template <class T>
class HasPrint1
{
public:
  struct type
  {
    enum { value = ( sizeof(dummy((T*)0)) == sizeof(yes_t) ) };
  };

  typedef char yes_t;
  struct no_t { yes_t[2] m; };

  template <class C>
  static yes_t dummy(C*, size_t = sizeof(&C::print1));

  static no_t dummy(...);
};

// same for HasPrint2


template <class T>
boost::enable_if< HasPrint1<T> > Print(const T& t) { t.print1(); }

template <class T>
boost::enable_if< HasPrint2<T> > Print(const T& t) { t.print2(); }

template <class T>
boost::disable_if< boost::mpl::or_< HasPrint1<T>, HasPrint2<T> > >
Print(const T& t) { std::cout << t << std::endl; }

Я позволил себе добавить опцию disable_if, чтобы показать сходство с блоком if / else if / else.

Буду рад некоторым отзывам.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...