0

arg1我需要一个带有两个参数的函数arg2

template<class T1, class T2>
SomeReturnType Foo(T1 arg1, T2 arg2);

参数可以是指针或std::iterator,或者是 random_access_iterator 的双向迭代器。Foo对这些迭代器进行一些操作,需要将迭代器返回给另一个对象,但返回的迭代器属于以下类型

ptr, T   -> iterator< iterator_traits<T>::iterator_category >
T,   ptr -> iterator< iterator_traits<T>::iterator_category >
ptr, ptr -> iterator< random_access_iterator_tag >

random_access_iterator, random_access_iterator -> iterator< random_access_iterator_tag >

random_access_iterator, T -> iterator< iterator_traits<T>::iterator_category >
T, random_access_iterator -> iterator< iterator_traits<T>::iterator_category >
T, T                      -> iterator< bidirectional_iterator_tag> >

我计划Foo根据参数的 iterator_category_tags 调用辅助函数,使用函数重载来处理调度。但我不知道如何计算Foo.

编辑:我现在看到了问题。的返回类型Foo派生自 std::iterator,并且可以是Foo函数的参数。这是一个问题,因为我一直在使用的特征类不是专门针对这些返回类型的,而是专门针对返回类型的基类的。我认为解决方案是使用is derived_from元函数。

EDIT2:标题显然不反映问题的内容。为了使它对其他人有用,我正在征求更好的标题的建议。

4

2 回答 2

1

您可以为此使用 boost 函数特征。看这里http://www.boost.org/doc/libs/1_52_0/libs/type_traits/doc/html/boost_typetraits/reference/function_traits.html

你可以像这样使用它:

boost::function_traits<FunctionSignature>::result_type
于 2012-11-27T10:56:31.047 回答
1

如果我正确理解您正在寻找一种从参数类型派生返回类型的方法,则可以以经典方式进行,如下所示(对于前几种情况):

#include <iterator>

template<typename T1, typename T2>
struct ret_iterator {};

// ptr, T   -> iterator< iterator_traits<T>::iterator_category >
template<typename P, typename T>
struct ret_iterator<P *, T>
{
  typedef std::iterator<typename std::iterator_traits<T>::iterator_category, P> iter;
};

// T,   ptr -> iterator< iterator_traits<T>::iterator_category >
template<typename T, typename P>
struct ret_iterator<T, P *>
{
  typedef std::iterator<typename std::iterator_traits<T>::iterator_category, P> iter;
};

// ptr, ptr -> iterator< random_access_iterator_tag >
template<typename P>
struct ret_iterator<P *, P *>
{
  typedef std::iterator<std::random_access_iterator_tag, P> iter;
};

// random_access_iterator, T -> iterator< iterator_traits<T>::iterator_category >
template<typename T>
struct ret_iterator<std::random_access_iterator_tag, T>
{
  typedef std::iterator<typename std::iterator_traits<T>::iterator_category, T> iter;
};

template<typename P, typename T>
struct ret_iterator<std::iterator<std::random_access_iterator_tag, P>, T>
{
  typedef typename ret_iterator<std::random_access_iterator_tag, T>::iter iter;
};
于 2012-11-27T11:25:57.250 回答