0

私は本当に複雑なクラスを持っています。それは別のクラスのベクトルの中にあります。とにかく、私が見つけた問題の中にある、より単純なものを報告します。

// the inner class
class DuffyDuck{
    int isblack;   // 0 is white, 1 is black
    int n_duck;
    vector<DuffyDuck> * point_Duck;
    public:
    DuffyDuck(int isblack):isblack(isblack){
    }
    void set_point(vector<DuffyDuck> & Abitants){
        point_Duck=&Abitants;
    }
};

// the complessive class

class DuckCity{
     vector<DuffyDuck> DuckAbitants;
     public:
     DuckCity(int numwhite,int numblack){

         for(int i=0;i<(numblack+numwhite);++i){
             DuckAbitants.push_back(DuffyDuck(i>=numblack));
             DuckAbitants[i].set_point(DuckAbitants);
         }

     }
};

これでうまくいきます (私はいくつかの関数で point_Duck を使用しています) が、そのようなことをすると、例で "(*point_Duck)[2].n_duck;" と呼ばれます。関数でプロジェクトがクラッシュします。

それは私がそれをした場合にのみ起こります:

DuckCity LittleTown(0,0);
LittleTown=DuckCity(3,5); 

そして、ポインタを呼び出すいくつかの関数を使用した後。

直接 LittleTown(3,5) を実行すると、すべて問題ありません。

十分に説明したことを願っています。

4

3 に答える 3

5

DuffyDuckクラスは のメンバーのアドレスを格納していvector<>ますDuckCity。したがって、 を別のインスタンスにコピーするDuckCityと、その新しいインスタンスには別のvector<>インスタンスが含まれます。ただし、DuffyDuckそのベクター内の各インスタンスには、古いDuckCityインスタンスの一部であったアドレスがまだ残っています。

したがって、あなたのコピーlittleTownはぶら下がっているポインターを生成します。

の設計を再考するか、 の各要素のディープ コピーを実行DuffyDuckする代入演算子を実装することをお勧めします。代入演算子を実装する場合は、Rule of Threeに従うことも忘れないでください。DuckCityvector<>

于 2013-09-26T19:31:25.813 に答える
0

この問題の原因は、各DuffyDuckが DuffyDuck のベクトルへのポインターを持っていることです。クラスが破棄されると、参照が無効になります --> クラッシュします。

DuckCity littleTown(1,2); // this creates a duck city 
                          // with each duck pointing to the DuckAbitans vector.
littleTown=DuckCity(3,5); // this initializes another instance (call it INST) 
                          // of DuckCity and
                          // then it assigns (via = operator) the value to littleTown
                          // by **copying** the DuffyDuck structures into a newly 
                          // allocated vector. This makes the pointer of each DuffyDuck
                          // invalid after INST is destroyed (as it is a temporary object)
于 2013-09-26T19:32:01.177 に答える
0

のアドレスをコピーするとAbitants、 によって作成された一時オブジェクトのベクトルのアドレスが取得されDuckCity(3,5)ます。この一時オブジェクトは にコピーされlittleTown、元のオブジェクトは破棄されます。これは、元のAbitatsポインターが未使用のメモリを指していることを意味し、それが原因でクラッシュが発生します。

これをどのように修正する必要があるかを正確に言うのは難しいです-おそらく、Abitatsポインターを「再構築」するコピーコンストラクターを持つことによって。

于 2013-09-26T19:32:46.903 に答える