2016-06-19 13 views
2

関数のパラメータにmalloc()returndの値を代入し、その関数の外部にアクセスすると...ここで何が間違っていますか? MYサンプルコード:mallocのセグメンテーションフォルト:

#include <stdio.h> 
#include <stdlib.h> 

struct student{ 
    double cgpa; 
    int id; 
    char name[100]; 

}; 

void init(student *ptr) 
{ 
    ptr = (struct student*)malloc(sizeof(struct student)); 
    ptr->id = 1; 
    ptr->cgpa = 4.00; 
    sprintf(ptr->name,"murad"); 
    printf("In Initfunc:\nname %s\nid %d\ncgpa %lf\n",ptr->name,ptr->id,ptr->cgpa); 
} 

int main() 
{ 
    struct student *murad; 
    init(murad); 
    printf("IN Main:\nname %s\nid %d\ncgpa %lf\n",murad->name,murad->id,murad->cgpa); 
    free(murad); 
    return 0; 
} 
+0

OT:BTW、これをCコンパイラでコンパイルすると、この無駄なmallocの結果のキャストを削除するだけです。 – alk

+1

この 'void init(student * ptr)'は無効です。C.これがコンパイルされた場合、C++コンパイラを使用してコンパイルされているようです。 – alk

答えて

1
printf("IN Main:\nname %s\nid %d\ncgpa %lf\n",murad->name,murad->id,murad->cgpa); 

これは、エラーの原因となっています。 muradのコピーであるstruct pointer inside functionにメモリを割り当てると、引数として渡します。したがって、mainのポインタにメモリが割り当てられておらず、参照解除された未初期化ポインタが未定義の動作を引き起こします

returnポインタから関数mainへのポインタが必要です。

だからあなたのプログラムは次のように行くことができます -

#include <stdio.h> 
#include <stdlib.h> 

struct student{ 
    double cgpa; 
    int id; 
    char name[100]; 
}; 

struct student * init(void) // <-- No need to pass any parameter 
{ 
    struct student *ptr = malloc(sizeof(struct student)); 
    ptr->id = 1; 
    ptr->cgpa = 4.00; 
    sprintf(ptr->name,"murad"); 
    printf("In Initfunc:\nname %s\nid %d\ncgpa %lf\n",ptr->name,ptr->id,ptr->cgpa); 
    return ptr;   // <--- return pointer 
} 

int main() 
{ 
    struct student *murad; 
    murad=init(); 
    printf("IN Main:\nname %s\nid %d\ncgpa %lf\n",murad->name,murad->id,murad->cgpa); 
    free(murad); 
    return 0; 
} 
1

問題は、新しいポインタを返すていないです。
はこれを試してみてください:

#include <stdio.h> 
#include <stdlib.h> 

struct student{ 
    double cgpa; 
    int id; 
    char name[100]; 

}; 

void init(struct student **ptr) 
{ 
    struct student *temp; 
    *ptr = (struct student*)malloc(sizeof(struct student)); 
    temp = *ptr; 
    temp->id = 1; 
    temp->cgpa = 4.00; 
    sprintf(temp->name,"murad"); 
    printf("In Initfunc:\nname %s\nid %d\ncgpa %lf\n",temp->name,temp->id,temp->cgpa); 
} 

int main() 
{ 
    struct student *murad; 
    init(&murad); 
    printf("IN Main:\nname %s\nid %d\ncgpa %lf\n",murad->name,murad->id,murad->cgpa); 
    free(murad); 
    return 0; 
} 

お知らせのinit

+0

新しいポインタも戻っていません。 – juanchopanza

+0

@juanchopanza:この文脈では「* return *」はあいまいです。 – alk

+1

@alkそうではないと思う。 – juanchopanza

1

あなたがinitの範囲でのみ使用することができ、ローカル変数ptrからmallocの結果を代入しているために二重のポインタを使用します。 mainのスコープ内のローカル変数muradに割り当てていません。

おそらくまたinit

から結果としてptrを返すために、より良いだろう、malloc関数の結果をキャストしないでください。それは貧弱なスタイルであり、潜在的に危険です。

関連する問題