2

複数の間接レイヤーを含むオブジェクト システムにラムダを格納しようとしています。g++ 4.7.1 を使用しています。

(同等の)オブジェクトをどのように正確に構築するかに応じて、ラムダは正しい値を持つ場合と持たない場合があります。

コード:

#include <iostream>
#include <functional> // used for std::function

using namespace std; // TODO nope

typedef function<int()> intf;


struct SaveLambda {
    const intf func;
    SaveLambda(const intf& _func) : func(_func) {}  
};


struct StoreSaved {
    const SaveLambda* child;
    StoreSaved(const SaveLambda& _child) : child(&_child) {
        cout << "Before returning parent: " <<  child->func() << endl;
    }
};


int main() {
    const int ten = 10;

    auto S = SaveLambda([ten](){return ten;});
    cout << "No indirection: " << S.func() << endl << endl;

    auto saved = StoreSaved(S);
    cout << "Indirection, saved: " << saved.child->func() << endl << endl;

    auto temps = StoreSaved ( SaveLambda([ten](){cout << "&ten: "<< &ten << endl; return ten;}) );
    cout << "***** what. *****" << endl;
    cout << "Indirection, unsaved: " << temps.child->func() << endl;
    cout << "***** what. *****" << endl << endl;

    cout << "ten still lives: " << ten << endl;
}

Compile as g++ -std=c++11 -Wall -o itest itest.cppand run: 異なる値を持つ 1 行の出力に注目してください。

私は何を間違っていますか?値によるキャプチャは、まあ、値によるキャプチャであると想定しました。(どちらも同じオブジェクトを参照しているにもかかわらず、34 行目とは異なり、StoreSaved の出力 (15 行目) が正しい値を生成していることに最も戸惑う点があります。唯一の違いは、別の間接レイヤーが追加されていることです。)

4

2 に答える 2

4

これは間違っています:

auto temps = StoreSaved(
                /* This temporary value dies at the last semicolon! */
                SaveLambda([ten](){cout << "&ten: "<< &ten << endl; return ten;})
                );

StoreSaved次に、存在しないオブジェクトへのポインタがあります。使用はUBです。

于 2012-09-05T01:09:11.300 に答える
1

他の人がすでに指摘しているように、問題は、一時的なものであるtempsため、存在しない構造体へのポインターで終わることです。SaveLambda

ポインターの代わりに、StoreSaved で SaveLambda 構造体を使用してコピーを保持できます。

struct StoreSaved {
   const SaveLambda child;
   StoreSaved(const SaveLambda& _child) : child(_child) {
       cout << "Before returning parent: " <<  child.func() << endl;
   }
};

また、ポインタを扱っていないため、child->func()すべてを to に変更する必要があります。child.func()

于 2012-09-05T04:39:21.557 に答える