2

基本的に私がここでやりたいことは、呼び出し元が本質的に特定の型を要求し、ポインターまたは参照が返されるテンプレート化された関数呼び出しを行うことです。テンプレートで指定された型に基づいて、取得した未調整のポインターがポインターの場合はそれを返し、格納された値の場合は型を参照に切り替えたいと考えています。また、この考えを拡張して、参照、クラス、クラスへのポインターなどを含めたいと思います...

#include <utility>
#include <type_traits>
using namespace std;
using namespace std::tr1;

template< bool condition, typename Then, typename Else >
struct IF {
    typedef typename Then RET;
};
template<typename Then, typename Else >
struct IF< false, Then, Else > {
    typedef typename Else RET;
};

template<class T>
struct ReturnType {

    typedef typename IF<std::is_pointer<T>::value, T, T& >::RET RET;

};

template<bool condition, typename U>
struct Member {
    Member(){ value = 2; member = &value; };
    int value;
    int* member;
};
template<typename U>
struct Member<false, U> {
    Member(){ member = 5; };
    int member;
};

typedef class tagFOO {
public:

    template < typename T >
    typename ReturnType<T>::RET function()
    {
        Member<std::is_pointer<T>::value, T> ret;

        return ret.member;
    };

} FOO;


int main() {

    int i = 0;
    int* pi = NULL;

    FOO A;

    i = A.function<int>();
    pi = A.function<int*>();

    return 0;
}

このコードは、出力 5 と 2 をそれぞれ実行したときに実行されます。

これを行う際の最初の問題は、これをやりたかった戻り値の型を定義することだったと思います

auto function()->decltype(typename ReturnType<T>::RET)

代わりは。これが機能しない理由がわかりません。想像できるすべての組み合わせで未解決のテンプレートエラーが発生するだけです。

私の 2 番目の問題は、さまざまな異なる戻り値の型を処理することです。これは少し試してみるつもりです。私が間違っている場合は修正してください。コンパイラは無効な戻り値を無視するように見えるため、末尾の戻り値の型は簡単に修正できます。これは単に ->decltype(T) を渡すだけでテストしたものですが、どこかでテストを間違えた可能性があります。

私がここに持っているものは、仕事を成し遂げるのに十分だと思います。なぜこれがそれほど素晴らしいアイデアではないのかについて、いくつかの意見があると思います。それらの意見を聞きたいです。

thx、BekaD:

4

1 に答える 1

1

boost::call_traits が役立つかもしれません。

http://boost.org/doc/libs/1_45_0/libs/utility/call_traits.htm

于 2010-12-31T01:59:37.417 に答える