5

空のデストラクタは何も実行せず、それを呼び出してもオブジェクトは削除されないと聞きました。しかし、コードでは:

#include <iostream>
#include <set>


class a
{
public:
    ~a() 
    {}
std::set <int> myset;
};

int main()
{
a object;
object.myset.insert(55);
object.~a();
object.myset.insert(20);
std::cout << object.myset.size();
}

*glibcが検出されました* /.app:doublefree orcorruption(fasttop):」そして「ABORT」が表示されます。

重要な場合は、c++11フラグを有効にします。では、空のコンストラクターは実際に何をするのでしょうか?それは何かをします、そして私はそれを読みません。

4

3 に答える 3

10

デストラクタは空に見えるかもしれませんが、実際にはメンバー変数を破壊しています。この場合、それは破壊的mysetであるため、後続insert(20)はクラッシュしています。

クラスに非PODメンバー変数がない場合、空のデストラクタは実際には何もしません。

于 2013-02-06T19:28:43.317 に答える
6

あなたの質問はいくつかの異なる問題に言及しています。

まず、エラーメッセージがあります。「ダブルフリー」は、おそらくデストラクタが2回呼び出されているためです。1回はユーザーによって、もう1回は変数がスコープ内になくなったときのC ++ランタイムによって(main関数の最後の括弧で)呼び出されます。

次に、空のデストラクタがオブジェクトを削除しないという質問があります。実際、オブジェクトはメモリから削除されませんが、メンバー変数は破棄されます。したがって、デストラクタを手動で呼び出した後も、のメモリobjectは割り当てられていmysetますが、無効になっています。

于 2013-02-06T19:34:18.127 に答える
1

スコープ外になると、デストラクタが呼び出されます。デストラクタを呼び出さずに、親クラスのメンバーまたはメンバー関数にアクセスすることを強くお勧めします。クラスにはメンバー変数mysetがあるため、手動で呼び出されたときにそれらの割り当てが解除され、セグメンテーションエラーが発生します。

オブジェクトを完全に使い終わったら、デストラクタを「クリーンアップ」と考えてください。いかなる状況でも、手動で呼び出すことはできません。

擬似コード:

class MyClass {
public:
  MyClass() {
    std::cout << "Constructor" << std::endl;
  }

  ~MyClass() {
     std::cout << "~Destructor" << std::endl;
   }
}

int main(int argc, char** argv) {
   MyClass myClass;
   return 0;
}

次の出力が表示されます。

Constructor

~Destructor

ご覧のとおり、手動で呼び出す必要はありません。

于 2013-02-06T19:30:16.027 に答える