2016-04-27 11 views
2

free()の動作の一部を理解できません。mallocポインタに等しいポインタを解放します。

int* ptr1 = (int*)malloc(sizeof (int)*10); 
int* ptr2 = ptr1; 
free(ptr2); 

free(ptr2)は自分のアレイを削除しますか?

私は何場合:このコードが正しい

int** ptr1 = (int**)malloc(sizeof (int)*10); 
int* ptr2 = (int*)malloc(sizeof (int)); 
*ptr2 = 10; 
ptr1[0] = ptr2; 
free(ptr1); 

ですか? free(ptr1)はptr2のスペースも削除しますか?

ありがとうございました

+0

、どちらか一方、両方ではない。しかし、私はクラッシュし、やけどこの例を投稿する誘惑を感じました。あなたが 'free'に与える唯一の情報は、ポインタの値です。第2の特有の工夫では、1つのメモリ空間しかシステムに戻されない。 –

+1

'valgrind'というツールがあります。これはあなたが探して使い始めることをお勧めします。あなたのプログラム内のメモリリークを表示します(ある場合)。 –

+2

'int ** ptr1 =(int **)malloc(sizeof(int)* 10);'でいくつかのポインタに必要なメモリを 'sizeof(int)* 10'を使って計算するコードはなぜですか? – chux

答えて

1
int* ptr1 = (int*)malloc(sizeof(int)*10); 
int* ptr2 = ptr1; 
free(ptr2); 

ptr2ptr1と同じ値が含まれているので、あなたがmalloc()に渡されたメモリはfree() dとします。

int** ptr1 = (int**)malloc(sizeof(int)*10); 
int* ptr2 = (int*)malloc(sizeof(int)); 
*ptr2=10; 
ptr1[0]=ptr2; 
free(ptr1); 

これは問題ではありません。配列ptr1に値ptr2を格納していますが、解放していません。あなたが欲しい:

int** ptr1 = (int**)malloc(sizeof(int*)*10); 
int* ptr2 = (int*)malloc(sizeof(int)); 
*ptr2=10; 
ptr1[0]=ptr2; 
... 
free(ptr1[0]); 
free(ptr1); 

ノートは、私はまた、intに(同じサイズではないかもしれない)だけではなく10 int秒10個のポインタを割り当てることmalloc()を変更しました。

最後に、don't need to cast the return value from malloc()がCであることに注意してください。それ自体は問題ではなく、あなたの質問とは無関係ですが、(間違いなく)悪いスタイルです。

+0

ありがとう!私が 'int tab [10]'で構造体を定義しているとします。次に、この構造体をmallocで作成し、freeで削除します。私のタブについて心配すべきですか? –

+1

@Kenshin: 'struct'を 'malloc()'に割り当てて 'free()'で解放すると、 'malloc()'で行った割り当てを解放しますが、構造体が参照するものは解放しません。単純なルールはすべての割り当てのためのものであり、 'free()'と一致する必要があります。 '再帰的な'無料の概念はありません。 – abligh

+0

はい、私のタブはmallocで作成されていませんでした。だから私のタブは私の構造体の一部と見なされるのか、それとも何とか削除すべきですか? –

3

はい、いいえ。

また、2番目の例のmalloc(sizeof(int)*10);が機能しますが、必ずしも10個のポインタのためのスペースを割り当てるわけではありません。することができますので、両方の変数が同じ値を含んでい

 
+------+ 
| ptr1 | ---\ 
+------+  \  +----------------------------+ 
       >---> | memory allocated by malloc | 
+------+ / +----------------------------+ 
| ptr2 | ---/ 
+------+ 

mallocによって返されたポインタ:


は、あなたがこのような何かを持っている ptr2への割り当て後、最初の例では何が起こるかを説明すると、それらのいずれかを使用して割り当てられたメモリにアクセスします。専用メモリは、メモリが ptr2によって指されることはまだそこに、アクセス可能であることを解放し、あなたが ptr1によってメモリポインタを解放すると

 
+---------+---------+---------+-----+ 
| ptr1[0] | ptr1[1] | ptr1[2] | ... | 
+---------+---------+---------+-----+ 
    | 
    | 
    v 
+----------------------------+ 
| memory allocated by malloc | 
+----------------------------+ 
^
    | 
    | 
+------+ 
| ptr2 | 
+------+ 

:2つ目の質問、何を持っていることは、このようなものであるために

ptr2まで結構です

+0

この質問はトピックから外れていますが、この数字? – orbitcowboy

+0

@MartinEttlいいえ、手作業でした。 :) –

+0

次に、[このディスカッション](http://unix.stackexchange.com/questions/126630/creating-diagrams-in-ascii/127782#127782)をご覧ください。利用可能なツールはたくさんあります。 – orbitcowboy

2

mallocおよびfreeあなたのデータ構造についてはわかりません。彼らが知っているのはバイトの塊です。

一般的に、mallocfreeコールの間には1対1の関係があります。 (例外はたくさんありますが、それは良い一般的なルールです。)

freeへの一回の呼び出しで、mallocへの2回の呼び出しによって割り当てられた2つのブロックが同時に解放されることはありません。

他の人が言っているように、質問に対する回答は「はい」と「いいえ」です。

0

空き(ptr2)は自分のアレイを削除しますか?

ここでは、用語deleteは使用できません。 GNU manualは言う:あなたは、もはやあなたはmalloc関数となったブロックを必要としない場合には、再び割り当てられるブロックが利用できるようにして自由 機能を使用

ただし、関数の戻り値の型自体がvoidであるため、freeは自動的にNULLにポインタを設定しません。また、

ブロックを解放するとブロックの内容が変更されます。 ブロックを解放した後にブロック内のデータ( ブロックのチェーン内の次のブロックへのポインタなど)を見つけることを期待しないでください。

私はそれを解放した後でポインタをNULLに設定する必要があるかどうかについて議論を喚起するつもりはありません。最初の例で

#include<stdio.h> 
#include<stdlib.h> 
int main() 
{ 
    int* ptr1 = malloc(sizeof(int)*10); 
    int* ptr2 = ptr1; 
    free(ptr2); 
    if(ptr2!=NULL) 
    { 
     printf("ptr is %p\n",ptr2); // still printf 
     printf("Enter a number for ptr2 :"); 
     scanf("%d",ptr2); 
     printf("Value pointed to by ptr2 : %d\n",*ptr2); 
     printf("Value pointed to by ptr1 : %d\n",*ptr1); 
    } 
    else 
     printf("Ptr2 pointed to null"); 
    printf("Size of ptr1 : %d\n",sizeof(ptr1)); 

    if(ptr1==NULL) 
     printf("ptr1 NULL\n"); 
    printf("Enter a number for ptr1 :"); 
    scanf("%d",ptr1); 
    printf("Value pointed to by ptr1 : %d\n",*ptr1); 
    printf("Value pointed to by ptr2 : %d\n",*ptr2); 

    free(ptr1); 
    if(ptr1==NULL) 
     printf("ptr1 freed\n"); 

    return 0; 
} 

出力

ptr is 0x1c92010 
Enter a number for ptr2 :4 
Value pointed to by ptr2 : 4 
Value pointed to by ptr1 : 4 
Size of ptr1 : 8 
Enter a number for ptr1 :1 
Value pointed to by ptr1 : 1 
Value pointed to by ptr2 : 1 
*** glibc detected *** ./testp: double free or corruption (fasttop): 0x0000000001c92010 *** 
Segmentation fault (core dumped) 
関連する問題