2011-03-19 4 views
1

간단하고 연결 목록을 사용하여 작업하고 있었고 이해할 수없는 것이 있다는 것을 깨달았습니다. 아래의 프로그램이 3을 인쇄하지 않는 이유는 무엇인지 알 수 없습니다 (난수를 인쇄합니다). 런타임시 오류가 없으며 y가 NULL이 아니라는 것이 이상하다고 생각합니다. Y를 변경하기 위해C에서의 간단한 포인터 문제 - 잘못된 값

struct ceva 
{ 
    int y; 
}; 

typedef struct ceva str; 

void do_something(str *x) 
{ 
    str *p = (str *)malloc (sizeof (str)); 
    p->y = 3; 
    x = p; 
} 

int main(void) 
{ 
    str *y; 
    do_something (y); 
    printf ("%d", y->y); 
} 
+0

+1 완전한 컴파일 가능한 프로그램을 제공합니다. 당신이''과''을 포함했다면 나는 +2를 주었을 것입니다. –

+0

감사합니다, 나는 가지고 있었지만 미리보기에 포함 된 것을 보지 못했습니다. 그래서 그들을 제거하기로했습니다. –

답변

1

, 그렇게 매개 변수를 do_something 것은 실제로 ** X

struct ceva{ 
int y; 
}; 
typedef struct ceva str; 
void do_something(str **x) 
{ 
str *p = (str *)malloc (sizeof (str)); 
p->y = 3; 
*x = p; 
} 
int main(void) 
{ 
str *y; 
do_something (&y); 
printf ("%d", y->y); 
} 
+0

do_something의 일부 스타일과 오타가 수정되었습니다. – amit

1

C 값에 의해 패스이며, 때문에, y str에해야합니다, & Y를 보낼 필요 그 상태가 main() 인 쓰레기를 가리키고 있습니다. 실제로 의도 한대로 수행하려면 do_something(..)이 str * 유형의 참조를 리턴해야합니다.

str* do_something(str *x) 
{ 
    str *p = (str *)malloc (sizeof (str)); 
    p->y = 3; 
    x = p; 
    return x ; 
} 

// 그리고 반환 값을 수집해야합니다.

str *y; // It's a good practice to set y to NULL. Do this instead. str *y = NULL ; 
y = do_something (y); 
+0

당신도 맞습니다. –

4

당신은 기능 do_something에 값 str x 지나가는 것입니다.

xdo_something으로 변경하면 main 기능에서 y가 변경되지 않습니다.

void do_something(str **x) 
{ 
    str *p = (str *)malloc (sizeof (str)); 
    p->y = 3; 
    *x = p; 
} 

int main(void) 
{ 
    str *y; 
    do_something (&y); 
    printf ("%d", y->y); 
} 

또는 함수가 할당 구조의 주소를 반환 do_something 확인 : 어느 다음에 y에 대한 참조를 전달하는 다음

C.이하기의 일반적인 방법
str *do_something(void) 
{ 
    str *p = (str *)malloc (sizeof (str)); 
    if (p) // ensure valid pointer from malloc. 
    { 
     p->y = 3; 
    } 
    return p; 
} 

int main(void) 
{ 
    str *y = do_something (y); 
    printf ("%d", y->y); 
} 
+0

나는 당신의 답을 고맙게 생각합니다. . –

1

x = p;로컬변수에 할당 된 메모리 위치에 할당 10은 즉시 잊혀진다. 하나 같이 할당 된 구조체의 주소를 반환 :

str* do_something() { 
    str *p = (str *)malloc (sizeof (str)); 
    p->y = 3; 
    return p; 
} 
int main() { 
    str * y = do_something(); 
    printf("%d", y->y); 
} 

또는 주소 [원문]에 쓸 수있는 주소 do_something을 제공 :

여기
void do_something(str** x) { 
    str *p = (str *)malloc (sizeof (str)); 
    p->y = 3; 
    *x = p; 
} 
int main() { 
    str* y; 
    do_something(&y); 
    printf("%d", y->y); 
} 
2

은 당신이 원하는 무엇 :

void do_something(str **x) 
{ 
    str *p = (str *)malloc (sizeof (str)); 
    p->y = 3; 
    *x = p; 
} 

int main(void) 
{ 
    str *y; 
    do_something (&y); 
    printf ("%d", y->y); 
} 

그렇지 않으면 전달 된 포인터의 복사본이 원하는 값으로 설정됩니다.

0

아래의 프로그램을 사용하십시오. 프로그램에 약간의 수정이 필요합니다.

struct ceva 
{ 
    int y; 
}; 

typedef struct ceva str; 

ceva* do_something() 
{ 
    str *p = (str *)malloc (sizeof (str)); 
    p->y = 3; 
    return p; 
} 

int main(void) 
{ 
    str *y = (str *)malloc (sizeof (str));; 
    y->y = 2; 
    y = do_something(); 
    printf ("%d", y->y); 
} 
+1

답변에 변경 사항에 대한 의견이 포함되어 있으면 더 가치가 있습니다 (변경 한 내용 및 이유). –