2013-04-06 2 views
1

array_push이라는 함수가 있다고 가정 해 봅시다. c.함수에서 C 배열에 대한 포인터 업데이트

void array_push(int *array_pointer, int array_length, int val) { 
    int i; 
    int *temp_array = malloc(sizeof(int) * (array_length + 1)); 

    for (i = 0; i < array_length; i++) { 
     temp_array[i] = *array_pointer; 
     array_pointer++; 
    } 

    temp_array[array_length] = val; 
    *array_pointer = temp_array; 
} 

어떻게 그것을 temp_array 새로운 배열을 사용할 수 있습니다 내 프로그램의 다른 부분을 가리 키도록 포인터 *array_pointer를 업데이트 할 수 있습니다? 나를

int t[2] = {0,2}; 
array_push(t, 2); 
/* t should now contain {0,2,3} */ 
+1

이 작업을 수행 할 수 없습니다. 't'는 포인터가 아니며 배열입니다. 배열의 크기를 변경할 수 없습니다. – Barmar

+0

@Barmar - 틀림없이 정확합니다. 처음 OP의 질문 중 일부를 알아 채지 못했습니다 ... – paulsm4

답변

2

처럼 뭔가를 할 수 있도록 허용 당신은 포인터에 대한 포인터로 array_pointer을 설정해야합니다

void array_push(int **array_pointer, int array_length, int val) { 

이 (여분의 별표를 참고).

또한 t이 포인터가 아니고 배열이되도록 호출 사이트를 변경해야합니다 (다른 곳에서는 배열 포인트를 만들 수 없습니다). 마지막으로 호출자가 배열의 새로운 크기를 알 수 있도록 array_length도 포인터로 전달해야합니다. 내가 힙에 t을 할당했습니다, 그리고 array_push() 내부 *array_pointer을 해제 한 방법

void array_push(int **array_pointer, int *array_length, int val) { 
    int *temp_array = malloc(sizeof(int) * (*array_length + 1)); 
    memcpy(temp_array, *array_pointer, sizeof(int) * *array_length); 
    temp_array[(*array_length)++] = val; 
    free(*array_pointer); 
    *array_pointer = temp_array; 
} 

int main() { 
    int n = ...; 
    int* t = malloc(sizeof(int) * n); 
    /* ... */ 
    array_push(&t, &n, 2); 
    /* ... */ 
    free(t); 
} 

참고 :

따라서, 코드의 전체 구조는 다음과 같을 수 있습니다. 이를 염두에두고는 array_push()의 논리의 많은 realloc()를 사용하여 단순화 할 수 있습니다

void array_push(int **array_pointer, int *array_length, int val) { 
    *array_pointer = realloc(*array_pointer, sizeof(int) * (*array_length + 1)); 
    (*array_pointer)[(*array_length)++] = val; 
} 
+0

realloc()을 재발 명했습니다. – Barmar

+0

@Barmar : 알아. 나는 그것을 향해 나아가고있다 (대답은 여전히 ​​진행중이다). – NPE

0

문제 1 :

다음

당신이 함수의 내부에 *의 int 배열을 만들거나 수정하려면, 대신

// WRONG: 
void array_push(int *array_pointer, int array_length, int val) { 
... 
    int *temp_array = malloc(sizeof(int) * (array_length + 1)); 
... 
    *array_pointer = temp_array; 

:

// BETTER: 
void array_push(int **array_pointer, int array_length, int val) { 
... 
    int *temp_array = malloc(sizeof(int) * (array_length + 1)); 
... 
    *array_pointer = temp_array; 
,369 당신은 "포인터 포인터의"를 전달해야

또는 :

// BETTER YET: 
int * array_push(int array_length, int val) { 
... 
    int *temp_array = malloc(sizeof(int) * (array_length + 1)); 
... 
return temp_array; 

문제 2 :

int t[2] = {0,2}; 같은 정적 배열을 선언 할 경우를, 당신은 임의로 크기의 변경할 수 없습니다. C를 공부하고 C++ 포인터와 배열이 동일하다는 것을 때 새로운 학생이 배우는 최초의 것들의

http://faq.cprogramming.com/cgi-bin/smartfaq.cgi?answer=1069897882&id=1073086407

하나 : 여기에 "포인터 대 배열"의 좋은 설명입니다. 당신은 통과별로 가치에 대해 혼란스러워 보이지만, 더 중요한 문제는 당신이 포인터에 대해 혼란스러워 보인다이다 :이 여기에 두 가지 문제가 있습니다

1

... 진실에서 추가 할 수 없습니다. int *array_pointer array_pointer는 배열이 아닌 int을 가리 킵니다. 배열의 첫 번째 int을 가리킬 수 있습니다. 관련이없는 메모에서 "int 배열에 대한 포인터"는 다음과 같이 보입니다 : int (*array_pointer)[array_length].

다음으로 돌아 가기 : int *array_pointer array_pointer는 int을 가리 킵니다. *array_pointer = temp_array;에서 *array_pointer이라는 표현식은 가리키는 객체를 제공하며 int을 저장할 수 있습니다. 하지만 temp_arrayint 값이 아닙니다.

array_pointer에 대한 변경 사항은 값 전달의 의미로 인해 호출자에게 표시되지 않는 문제를 해결하려고 시도하고 있음을 알 수 있습니다. 따라서 호출자가 제공하는 int *을 가리키고 호출자의 int *을 수정하도록 array_pointer을 변경하거나 반환 유형을 사용하여 새 포인터를 반환해야합니다. 결국 두 옵션 모두 두 가지 문제를 모두 해결합니다.

관련 문제