2012-03-05 6 views
1

次のコードがメモリリークを生成しているかどうかを判断する最善の方法を知りたいのですが、メモリを解放する必要があることを理解していますが、同時にこの配列またはintへのポインタはスコープの外に関数が返ってきたら、それを解放するかどうかは関係ありません。このコードはメモリリークを生成していますか、それともきれいですか?

しかし、私はVisual Studioで、少なくともマイクロソフトデバッガによると、2010年

そして、これはあなたがメモリをチェックするあなたの方法を説明してください可能性がどのように最善のアプローチ学習のためにヒープを中断せずにメモリを解放することはできません。この特定のケースでは漏れ。事前

#include <iostream> 
#include <algorithm> 
#include <cmath> 

using namespace std; 
int sieve(int n) 
{ 
    int *a = (int *) malloc(sizeof(int) * n); 
    int max = floor(sqrt((double)n)); 
    int p = 2; 
    memset(a,0,sizeof(int) * n); 
    while(p<=max) 
    { 
    for(int i = 2 * p; i <= n; i+= p) 
     a[i] = 1; 
    while(a[++p]) /* Empty */ ; 
    } 
    while(a[n]) n--; 
    /* free(a); */ // free our array as we are done with it. but it generate a heap error 
    return n; 
} 
int main(void) 
{ 
    cout << sieve(100) << endl; 
    system("pause"); 
    return 0; 
} 
+1

あなたが境界アクセス、したがって、おそらくあなたの解放エラー – Anycorn

+0

のうち、あなたのためにこれをデバッグする時間がないが、valgrindのあなたは 'alloca'で見たいと思うかもしれませんメモリの読み取り/書き込みエラー – kfmfe04

+0

があると言う - のhttp:/は/www.mkssoftware.com/docs/man3/alloca.3.asp – sje397

答えて

3

割り当てられたメモリを解放していないので、プログラムにメモリリークがあります。 ここでmallocを使用していて、 "new"を使用して "delete"演算子を使用する場合は "free"を使用してください。 return文の前にメモリを解放してみます。 valgrindツールを使用して、プログラム内のメモリリークを確認することもできます。 詳細については、urlをご確認ください。

このツールは、プログラムでメモリリークを検出するのに役立ちます。

+0

私はあなたがもっと傾けるための道具を使って私の質問に答えてくれてありがとうと思います。これはすべてのところに行きます。私は上記の例が悪いことを知っています。 C + +と純粋なCと純粋なCで書かれることができますが、私はそれのほとんどを理解しているかどうかを確認するための高速テストでした。 –

2

おかげではい、それはスタンドとしてあなたのプログラムがメモリリークが発生します。一般的に

あなたは(Cでmallocを使用して、またはC++でnew)動的にメモリを割り当て、そしてあなたがスマートポインタを使用していないしている場合、あなたはそれぞれfreeまたはdeleteを使用してメモリを解放する必要があります。

特定のテストプログラムでは、sieve()メソッドを呼び出した直後に終了します。これは、割り当てられたメモリがオペレーティングシステムによって自動的に割り当て解除されることを意味します。

はまた、あなたがC++Cコードを書いているように見えることに注意してください:

  • mallocは、メモリを割り当てるためのCの方法です。生ポインタを使用する必要がある場合は、代わりにC++でnewを使用する必要があります。
  • vectorのような標準ライブラリコンテナを使用すると、自動的にメモリが管理されます。
3

このラインはあなたのエラーの原因である可能性があります。ここでは

for(int i = 2 * p; i <= n; i+= p) 

あなたはループinからまたは等しい小さいながら。しかし、すべての配列と同様に、インデックスは0から(size - 1)になる必要があります。あなたは0からn-1にインデックスさn int型を、割り当てている

int *a = (int *) malloc(sizeof(int) * (n + 1)); 
0

:あなたは、配列のための1つの余分なエントリを割り当てる必要があります。ただし、4からnまでをループしています。つまり、インデックスnと壊れたメモリを割り当てます。そのため、freeがエラーを引き起こしています(呼び出したときに破損がないかどうかを確認します)。

メモリ破損を修正してから、freeコールを戻す必要があります。

1

もっと重要なこと:

あなたはint *a = (int *) malloc(sizeof(int) * n);n int型を割り当てました。この情報にアクセスするには、0からn-1までに開始する必要があります。 while(a[n]) n--;行では、割り当てられたメモリセクションの範囲外です。多分コア!

a[n]の値がすべて0の場合はどうなりますか?負の値に達するまでnを減らします。これはどうですか? a[n]の値にはn < 0でアクセスします。多分別のコア。

これはC/C++です。それはあなたが書いたすべてを実行するので、注意してください!

一般的なプログラミング技法:

  • すべての配列の制限を確認してください。
  • malloc戻り値を確認します。
  • 必ずfreeまたはdeleteあなたのポインタ
  • 使用正しいタイプ:nは多分unsignedになり、それを使用!
関連する問題