-3

重複の可能性:
「new」を使用するとメモリリークが発生するのはなぜですか?

私はこのような小さな問題に遭遇しました

int main() {
    int i = *new int;
    delete &i;
    return 0;
}

コンパイルは問題ありませんが、実行すると、シェルは次のように表示します。

a.out(38303) malloc: *** オブジェクト 0x7fff5fbff8cc のエラー: 解放されるポインターが割り当てられませんでした
*** デバッグするために malloc_error_break にブレークポイントを設定します
トラップの中止

その間

int main() {
    int *i = new int;
    delete i;
    return 0;
}

期待どおりに正常に実行されます。

私を悩ませているのは、最初のケースでは「new」演算子を使用してメモリを割り当てていないということですか? 削除するとエラーになるのはなぜですか?

Webで何度か検索しましたが、適切な説明が見つかりません。なぜそれが間違っているのか誰か教えてもらえますか?ありがとう :)

4

5 に答える 5

11

問題は、メモリ リークがあり、動的に割り当てられていないものを削除していることです。なんで?を動的に割り当てるため、その値intをにコピーしますii次に、オブジェクトへのポインターを介してオブジェクトを削除しようとしましたiが、動的に割り当てられませんでした。その値は、何かから初期化されただけです。実際に動的に割り当てたオブジェクトへのポインタを失いました。

ダイアグラム的には、まず、動的ストレージ期間をnew int持つオブジェクトを作成し、intその int へのポインターを返します。

        _____        ______
Heap:  | int | <--- | int* |
       |_____|      |______|

次に、ポインターを逆参照してオブジェクトを提供し、その値を自動保存期間intを持つオブジェクトにコピーします。この後、どこにも保存しなかったため、int取得したポインターは失われます。new

        _____
Heap:  | int |
       |_____|
        _____
Stack: | int |
       |_____|

次に、自動保存期間付きのアドレスを取得して、それintを試みdeleteます。

        _____
Heap:  | int |
       |_____|
        _____        ______
Stack: | int | <--- | int* | <-- Cannot delete because it was
       |_____|      |______|     not dynamically allocated
于 2012-12-21T16:09:05.877 に答える
10

おそらくあなたが書きたかったのはこれです:

int main() {
    int& i = *new int;   // note the reference type
    delete &i;
    return 0;
}

しかし、そのコードを見たとしても、正気の人間は誰もあなたを雇わないことに注意してください。

于 2012-12-21T16:14:34.237 に答える
3

最初のケースでは、「new」演算子を使用してメモリを割り当てませんか?

確かにそうです。しかし、あなたはそれへのポインタを保持していません。代わりに、その(初期化されていない)値をローカル変数にコピーし、割り当てられたメモリをリークします。メモリへの唯一のポインタを失ったので、それを削除する方法はありません。

削除するとエラーになるのはなぜですか?

割り当てられたメモリではなく、&iローカル変数を指しているためです。ローカル変数を含め、iが割り当てられていないものを削除するとエラーになります。new

于 2012-12-21T16:12:55.880 に答える
3

delete &ideleteによって返されなかったポインターを試みているため、失敗しますnew。これは未定義の動作です。

int i = *new int;

に新しく割り当てられた の値を割り当ててます。ポインターが失われています。inti

于 2012-12-21T16:08:50.223 に答える
1
int main() {
    int i = *new int;
    delete &i;
   return 0;
}

最初の行は ののみを設定しますi。それはまだスタック上にあるため、そのアドレスを に渡すことは違法deleteです。

于 2012-12-21T16:09:37.720 に答える