2

ユーザー定義型をサポートできるmin、 、maxなどの一連の関数を設計したいと考えています。stddev私が計画しているのは、ユーザーがExtractorこれらの関数にテンプレート引数を渡せるようにすることです。次のようないくつかのサンプル コード:

template <typename T>
struct DefaultExtractor
{
  typedef T value_type;
  static T value(T &v){
    return v;
  }
};

template <
  typename Extractor=DefaultExtractor<typename std::iterator_traits<InputIterator>::value_type>, //error
  typename InputIterator>
typename Extractor::value_type 
foo(InputIterator first, InputIterator last)
{
  return Extractor::value(*first);
}

これはコンパイルされず、エラー メッセージは "エラー: 'InputIterator' はこのスコープで宣言されていません" の行にありtypename Extractor=...ます。

Extractorテンプレートを前に置きたい理由InputIteratorは、ユーザーがfooカスタマイズされたを呼び出したいときExtractorに、 の型を明示的に指定する必要がないからですInputIterator

コードをコンパイルするための解決策があり、同時にInputIteratorカスタマイズExtractorが必要な場合にユーザーがパラメーターを明示的に提供する必要がないかどうか疑問に思います。

コードは でコンパイルされg++-4.6.1 -std=c++0xます。

4

1 に答える 1

3

エクストラクターをテンプレート パラメーターとして渡したいと思われますが、実際には関数にオブジェクトを渡す方が一般的です。また、extractor に渡すことができる追加の状態を持つことができるため、より柔軟です。

最も重要なことは、テンプレート パラメーターの処理が簡単になることです。

#include <iterator>
#include <list>

template <typename T>
struct DefaultExtractor
{
  typedef T value_type;
  static T value(T &v){
    return v;
  }
};

struct MyExtractor {
  typedef int value_type;
  static int value(int value) { return value; }
};

template <typename Extractor, typename InputIterator>
inline typename Extractor::value_type
foo(
  InputIterator first,
  InputIterator last,
  const Extractor &extractor
)
{
  return extractor.value(*first);
}

template <typename InputIterator>
inline typename DefaultExtractor<
  typename std::iterator_traits<InputIterator>::value_type
>::value_type
foo(
  InputIterator first,
  InputIterator last
)
{
  typedef DefaultExtractor<typename std::iterator_traits<InputIterator>::value_type> Extractor;
  return foo(first,last,Extractor());
}


int main(int argc,char **argv)
{
  std::list<int> l;

  // Use default extractor
  foo(l.begin(),l.end());

  // Use custom exractor.
  foo(l.begin(),l.end(),MyExtractor());
  return 0;
}
于 2012-09-04T04:11:10.747 に答える