1

私はこのようなコードをいくつか持っています.vecはある種のベクトルクラスです:

Vec Vec::choose(const Vec& ifPositive, const Vec& ifNegative) const {
    Vec out(mSize);
    for(int index = 0; index < mSize; ++index) {
        if(mData[i] > 0)
            out[i] = ifPositive[i];
        else
            out[i] = ifNegative[i];
    }
    return out;
}

現在、このコードは一般的に問題なく動作しますが、関数の左側が引数の 1 つである場合、不要なコンストラクター/デストラクター呼び出しがいくつかあります。

curVal =  trigger.choose(posVal, curVal); // construct is called in choose, then old curVal is destroyed

これを改善/回避する方法はありますか?関数の左側が別のコードを実行するパラメーターの 1 つであることをコンパイラーが認識した場合などです。

編集: ここにいくつかのサンプル コードがあります: http://ideone.com/nPUK3h

最後の (4.) 構造を省略できるかどうか知りたいです。後で自宅で、より高度な最適化を行ってこれをコンパイルします。

Edit2: 次の追加機能を導入すると、追加の構築を回避できます。

Vec& Vec::setNegative(Vec& target, const Vec& ifNegative) const {
   for(int index = 0; index < mSize; ++index) {
        if(mData[index] <= 0)
            target[index] = ifNegative[index];
    }
    return target;
}

したがって、choose-function の lhs が最初のパラメーターと同じである場合、これは同じ出力を生成しますが、lhs が別のベクトルである場合は、代わりに新しいベクトルを取得したいと考えています。

いくつかのテンプレート マジックまたはコンパイラ テクノロジを介して 2 つの間で選択する方法はありますか??

4

2 に答える 2

1

IIRC、RVO では、コンパイラが受信オブジェクトの場所に戻り値を構築することを許可していますが、この場合、そのオブジェクトへの参照が呼び出しで使用されています。つまり、パラメーターが使用される前に戻り値が構築されています。

したがって、これが RVO をどのように打ち負かすかがわかります。しかし、なぜそれが移動を打ち負かすのかわかりません。

于 2013-06-27T12:29:05.810 に答える