2016-07-01 9 views
0

私は次のようになり、いくつかの(レガシー)コードがあります。これは非常に古いコードであると私は、これはここで起こっているダウンキャストの並べ替えを行うには恐ろしい方法であることを認識コンパイラがstatic_castの型パラメータを推論できないのはなぜですか?

void castFoo(string type, void* foo) { 
    FooA* foo_a = NULL; 
    FooB* foo_b = NULL; 

    if (type == "A") { 
    foo_a = static_cast<FooA*>(foo); 
    } else { 
    foo_b = static_cast<FooB*>(foo); 
    } 

    // now do things with one of the two foo's 
} 

を。しかし、それは私を不思議に思った:なぜ私はこれのように書くことができないのですか?

if (type == "A") { 
    foo_a = static_cast(foo); 
    } else { 
    foo_b = static_cast(foo); 
    } 

確かに、コンパイラにとっては曖昧であり、関数の中では通常のテンプレート引数の減算のように見えます。ここでタイプ控除が行われないのはなぜですか?

+3

あなたの意見では、 'decltype(static_cast(foo))'や 'decltype(static_cast (foo))'の型であるべきですか?表示されているような表現が表示されているときの意味と同じでない場合は、ジェネリックプログラミングにとってはそれほど恐ろしいものではありませんか? –

+0

'std :: string var; var = static_cast(物); 'キャストがキャストできる_three_' operator = 'があります。 –

+0

'static_cast(foo)'の型はどのように推論すべきですか? –

答えて

3

静的キャストは危険です。この場合、voidへの/からのキャストは、まったく同じ型にする必要があります。

暗黙的なtypimgは、2つのキャストが未定義の動作を生成するように、キャストに直接隣接しないコード変更を許可します。

好きなようにコードを作ることができますが、それはあまり知られていません。

template<class V> 
struct implicit_static_cast_t{ 
    V v; 
    template<class T> 
    operator T()&&{ 
    return static_cast<T>(std::forward<V>(v)); 
    } 
}; 

template<class In> 
implicit_static_cast_t<In> 
auto_static_cast(In&& in){ 
    return {std::forward<In>(in)}; 
} 

は今、あなたのようなauto_static_cast振る舞いはstatic_cast振る舞うようにしたいです。

関連する問題