1

ここで私のコードで何が起こっているのか説明できますか? デストラクタを正しく使用しているか、構造体で使用していないかはわかりません。

そこにデストラクタがあると、次のようになります:
function1: 23
function2: 8.86183e-317
* glibc が検出されました./a: 二重解放または破損 (fasttop): 0x000000000111b010 * *

デストラクタをコメントアウトすると、次のようになります:
function1: 23
function2: 24

それが私が欲しいものです。しかし、より複雑なプログラムのメモリ リークを回避するためにデストラクタは必要ではないでしょうか。

(ご覧のとおり、ポインター/割り当て全般について少し混乱している可能性があります)

ありがとう!

編集:そうそう、なぜ function1 の余分な割り当てステップが違いを生むのですか?

Edit2:コンストラクターで x = 0 を初期化する必要がありますか? 私はそれが適切だと思いました...これを行うときに初期化時に割り当てる必要がありますか? 代わりに: x = gsl_vector_alloc(1)。

#include <iostream>
    using namespace std;
#include <cassert>
#include <cmath>
#include <gsl/gsl_vector.h>

struct struct1{
    gsl_vector * x;

    struct1() {
        x = 0;
    }
    ~struct1() {
        if (x) gsl_vector_free(x);
    }
};

void function1(void *p) {
    struct1 s = *(struct1 *) p;
    s.x = gsl_vector_alloc(1);
    gsl_vector_set(s.x, 0, 24);
}

void function2(void *p) {
    struct1 s = *(struct1 *) p;
    gsl_vector_set(s.x, 0, 24);
}

int main() {
    struct1 s;
    s.x = gsl_vector_alloc(1);
    gsl_vector_set(s.x, 0, 23);

    function1(&s);
    cout << "function1: " << gsl_vector_get(s.x, 0) << endl;

    function2(&s);
    cout << "function2: " << gsl_vector_get(s.x, 0) << endl;

    return 0;
}
4

1 に答える 1

1

内部でfunction1、関数で作成したオブジェクトfunction2のコピーを作成します。これらのコピーには同じポインタがあります。これらの各コピーのデストラクタが呼び出されると、が呼び出されるため、同じポインタで 3 回呼び出そうとします。struct1main()xgsl_vector_free

  • いつかは破壊さfunction1れるs
  • いつかは破壊さfunction2れるs
  • いつかは破壊さmainれるs

このクラスのコピー コンストラクターとコピー代入演算子を実装する必要があります。リソースを所有するクラスがある場合は常に、これら 2 つの関数とデストラクタを実装する必要があります。リソースとは、使い終わったときにクリーンアップする必要があるものです。

サンプル コードでは、すべての割り当てと割り当て解除をクラス内にカプセル化して、クラスを気にせずに使用できるようにする方がはるかに優れています。クラスが実際にそのリソースを管理するようにします。

于 2010-12-03T18:13:34.650 に答える