0

構造体/オブジェクトへのポインターがあり、その構造体/オブジェクトに他のオブジェクトへの他の2つのポインターが含まれており、「保持しているポインターを破壊せずに2つのポインターを含むオブジェクト」を削除したい場合-どうすればよいですか?

オブジェクト A へのポインター (オブジェクト B へのポインターを含み、オブジェクト C へのポインターを含む)。オブジェクト A の削除 オブジェクト A へのポインタは削除されますが、オブジェクト B / C へのポインタはまだ存在します。

この仕事をするために私がしなければならないことはありますか?

アップデート

これはゲーム プロジェクト用です。これで説明がつくことを願っています。現在、最初の構造体 (A) 内に B、C への 2 つのポインターを配置しても、いくつかの「問題」があります。

struct Player
{
    char * Name;
    Weapon* PlayerWeapon;
    Armor* PlayerArmor;
};

struct Weapon
{
    char * Name;
    int Damage;
};

struct Armor
{
    char * Name;
    int Resistance;
};

そして、これはどういうわけか機能しません。

Player* CreatePlayer(char * Name, Weapon* weapon, Armor* armor)
{
    Player *pPlayer = new Player;

    pPlayer->Name = name;
    pPlayer->Weapon = weapon;
    pPlayer->Armor = armor;
};

そして後でプレイヤーが「死ぬ」とき、装備は削除されるべきではありません。

4

5 に答える 5

3

ポインター (A) 内に含まれるポインター (B & C) は、デストラクタを介して明示的に削除しない限り削除されません。ただし、ポインター A を削除すると、ポインター A を使用して B & C にアクセスすることはできません。

注: 浅いコピーを避けるために、クラス A にコピー コンストラクターと = オーバーロードされた演算子が必要です。

他のプレイヤーに同じ鎧と武器を使用したい場合は、プレイヤーのデストラクタで武器と鎧を削除していないことを確認してください。次に、このように別のプレーヤーに同じポインターを使用できます。

Weapon* weapon = CreateWeapon();
Armor* armor   = CreateArmor();

Player* player1 = CreatePlayer("Alpha", weapon, armor);
delete player1;

Player* player2 = CreatePlayer("Beta", weapon, armor);
delete player2;
于 2012-06-22T08:28:56.467 に答える
1

オブジェクト A へのポインター (オブジェクト B へのポインターを含み、オブジェクト C へのポインターを含む)。オブジェクト A の削除 オブジェクト A へのポインタは削除されますが、オブジェクト B / C へのポインタはまだ存在しますか?

いいえ未定義の状態です。彼らには何でも起こりえます。あなたのシステムにあるかもしれませんが、それらが存在することに気づきますが、それは単なる幻想であり、毎回保証されるわけではないと想定します.

を削除するとすぐに、そのA*すべてのコンテンツが次回のダイナミック アロケーションで利用可能になります。おそらく、後で他のオブジェクトに割り当てられる可能性があります。システムによって0は、削除されたものをすべてアウトする場合があります。繰り返しますが、何でも起こり得ます!

この仕事をするために私がしなければならないことはありますか?

を削除する前にB*、および他のポインターに保存します。オブジェクトは無傷で、そのアドレスが保存されているため、完全に問題ありません。C*A*

于 2012-06-22T08:27:50.743 に答える
1
struct Foo
{
   A *a;
   B *b;
}

Foo *foo = new Foo();
delete foo; //foo now points to garbage. you can't use it
foo = nullptr; //don't use foo!

しかし、あなたはそうすることができます:

Foo *foo new Foo();
//do some stuff with foo
A *a = foo->a;
B *b = foo->b;
delete foo;
foo = nullptr;
// if Foo does not destroy objects pointed by a,b in destructor you can still
//use them through a,b vars
a->doSomeStuff(); //ok
b->doSomeOtherStuff(); //ok

編集

あなたの場合、鎧と武器は破壊されません。それらへのポインタを失うだけです(そしてメモリリークが発生します)。std::vectorポインターを保持するために、すべての鎧と武器をいくつかのコンテナー ( など) に保持することをお勧めします。

于 2012-06-22T08:25:37.233 に答える
0

最初に a と b のコピーを作成しないと、これは不可能だと思います。

于 2012-06-22T08:27:41.520 に答える
0

「ネイキッド」ポインタの使用は避けるべきです。shared_ptrまたはなどのスマート ポインター クラスを使用することをお勧めしますunique_ptr。彼らはnewとを処理deleteしますが、これは補助なしで完全に正しく行うのは非常に困難です。これらはBoostにあり、おそらくコンパイラに付属してshared_ptrいるTR1ライブラリ( )にもありますが、コンパイラがより新しい場合はそのままです。std::tr1::std::

あなたはプログラムについてあまり語っていませんが、ポインタを保存するために何かをする必要がある場合、オブジェクトAには B と C へのポインタの唯一のコピーがあるように思えます。それは の仕事ですunique_ptr

C++11 では、

struct A_type {
    std::unique_ptr< B_type > B; // Object *owns* B and C
    std::unique_ptr< C_type > C;
};

std::unique_ptr< A_type > A( new A_type );

auto my_B = std::move( A->B ); // Acquire ownership away from object
auto my_C = std::move( A->B );
A.release(); // Delete object and anything it owns (at this point, nothing)

// my_B and my_C are guaranteed to be destroyed at some appropriate time
于 2012-06-22T08:38:48.753 に答える