質問

のファンクターバージョンを実装しようとしています static_cast で使用するため std::bind().

ブーストを知っています ll_static_cast<K>() (見る boost :: bindでstatic_castを使用します)、しかし、私は今ブーストを使用していません。

コードの例があります なぜいくつかの標準オペレーターに標準的な機能を持っていないのですか? しかし、GCC 4.2.1でコンパイルされません:

template <typename Target>
struct StaticCast
{
    template <typename Source>
    Target operator()(Source&& source) const
    {
        return static_cast<Target>(source);
    }
}

コンパイルするものを手に入れることができましたが、それが正しいかどうかはわかりません:

template <class Target>
struct StaticCast : public std::unary_function<void, Target> {
    template <class Source>
    Target operator()(Source& src) const {
        return static_cast<Target>(src);
    }
};

このバージョンが正しいかどうか、そしてもしそうなら、なぜ必要なのか教えてもらえますか std::unary_function 前のコードの例では使用されていませんか?

使用法:

std::vector<BaseObject*> vec;  // BaseObject* are known to be of type 
    // DerivedObject* of course, please don't ask me how or why...

std::for_each(vec.begin(), vec.end(),
    std::bind(&DerivedObject::doStuff,
        std::bind(StaticCast<DerivedObject*>(), std::placeholders::_1),
    "with some string"));
役に立ちましたか?

解決

C ++ 03での完全な転送がないことを考えると、過負荷を使用する必要があります。

template<class Target>
struct StaticCast
{
    typedef Target result_type;

    template<class Source>
    Target operator ()(Source& src) const
    {
        return static_cast<Target>(src);
    }

    template<class Source>
    Target operator ()(Source const& src) const
    {
        return static_cast<Target>(src);
    }
};

明示的に作成していることに注意してください typedef 為に result_type 継承するのではなく std::unary_function<>. 。その理由は、最初のテンプレートパラメーターです std::unary_function<> あるはずです operator()'の引数タイプですが、私たちのからです operator() 事前にこれを知ることができないテンプレートなので、そもそもそれを提供することは不誠実です(特に void, 、それはそれを意味します operator() 実際、それが統一されている場合)です。


また、完全性のために、ここにファンクターの正しいC ++ 11バージョンがあります:

template<class Target>
struct StaticCast
{
    template<class Source>
    Target operator ()(Source&& source) const
    {
        return static_cast<Target>(std::forward<Source>(source));
    }
}

他のヒント

最初の1つが機能しない理由の1つは、おそらくC ++ 11をサポートしていないコンパイラでRValue参照を使用しているためです。

あなたが必要とする理由 std::unary_function 有効にすることです std::result_of あなたのクラスのために std::bind C ++ 98には逆タイプがないため、結果タイプを推定するために使用します。

あなたが見たら std::unary_function タイプを定義していることがわかります result_type あなたが渡すテンプレート引数から、それは std::result_of また std::bind 直接。

まあ、一般的にあなたのコードは悪いです:

まず、それらの非コンスト参照を要求しながら、一時的なオブジェクトとR値で問題があるかもしれません

例えば

float f = StaticCast<float>()(4);

コンパイルさえしません。

次にあなた コピーを作成します キャスト中のオブジェクトの。それはあなたが望むものではないかもしれません。

ソースの例 自由 その欠点の move セマンティクス

ライセンス: CC-BY-SA帰属
所属していません StackOverflow
scroll top