1

したがって、関数 f が与えられた場合、いくつかのマクロ foo を使用せずに、特定の個別の無関係なクラスの特定の動作を定義する方法があります。

例:と同じことを達成するための代替/方法:

//p for param

template<typename T> 
T f(T p){ // some default op}; 

template<>
T f<float>(T p)
{ return 2*p; }

template<>
T f<double>(T p)
{ return 2*p; }

template<>
T f<int>(T p)
{ return 2*p; }

template<>
T f<std::string>(T p)
{ //return p copies of the string appended together; }

template<>
T f<std::vector>(T p)
{ //return the vector's element's copied}

// etc

いいえ、通常のオーバーロードは好きではありません。理想的にはテンプレートのようなもの

if T in [int, float, double]
T f(T p) { return 2*p; }

else // デフォルトのその他の動作を定義します。Pythonでできること。

とにかく、Tのクラスに基づいて決定を下すには?私が考えることができる可能な解決策は、非常に...かなりではありませんが、typeidとデマングリングを使用することです。

何らかの理由で、スーパージェネリック関数と約 15 の異なるクラスがあり、オーバーロードを使用するすべてがきれいではないと書いているとします。

4

2 に答える 2

5

あなたの質問を正しく理解できたら、他のすべてのタイプとは異なる方法で処理する必要があるタイプのリストを作成しますか?

その場合は、目的の型のリストを作成し、メタ関数を使用して、T が true または false を返す型のリストにあるかどうかを判断します。

次に enable_if を使用して関数の実装を切り替えます。

#include <boost\mpl\vector.hpp>
#include <boost\mpl\contains.hpp>

typedef boost::mpl::vector<char,int,unsigned,long,unsigned long> types;
template<class T>
typename std::enable_if<boost::mpl::contains<types,T>::value, T>::type 
    foo(T t) 
{
    std::cout << "special foo\n";
    return t;
}

template<class T>
typename std::enable_if<boost::mpl::not_<boost::mpl::contains<types,T>>::type::value, T>::type 
    foo(T t) 
{
    std::cout << "normal foo\n";
    return t;
}
void main()
{
    foo(1);   //calls special foo because int is in the list
    foo(1.1); //calls normal foo because float is not in the list
}

更新: boost.MPL は古くなっています。C++11 をサポートしている場合は、brigand を使用してください

于 2013-06-28T19:19:38.860 に答える