배열은 함수 경계를 넘는 순간 첫 원소 포인터처럼 전달되므로, 길이와 읽기/쓰기 의도를 같이 선언해야 합니다.
- 함수 인자의
int arr[]가 진짜 배열인지 포인터인지 다시 확인하고 싶다 - 길이를 같이 넘겨야 하는 이유를 설명해야 한다
- 읽기 전용 배열 인자에
const를 어디에 붙이는지 헷갈린다
숏컷 코드
int sum_array(const int *arr, size_t n);문법
함수 매개변수의 int arr[]는 겉보기만 배열이고, 실제로는 int *arr처럼 동작합니다.
void print_array(const int arr[], size_t n) {
for (size_t i = 0; i < n; i++) {
printf("%d\n", arr[i]);
}
}위 선언은 아래와 같은 의미로 읽어도 됩니다.
void print_array(const int *arr, size_t n);핵심은 두 가지입니다.
- 배열 전체가 함수로 복사되지 않습니다.
- 길이 정보는 자동으로 따라오지 않습니다.
전달 규칙
배열을 읽기만 하는 함수라면 const를 붙여 의도를 분명히 하는 편이 좋습니다.
int sum_array(const int *arr, size_t n) {
int total = 0;
for (size_t i = 0; i < n; i++) {
total += arr[i];
}
return total;
}반대로 원본을 수정하는 함수라면 const를 빼고, 길이 인자는 그대로 유지합니다.
void zero_array(int *arr, size_t n) {
for (size_t i = 0; i < n; i++) {
arr[i] = 0;
}
}체크포인트
함수 밖에서는 sizeof arr / sizeof arr[0]로 길이를 계산할 수 있습니다.
int data[] = {10, 20, 30, 40};
size_t n = sizeof(data) / sizeof(data[0]);
print_array(data, n);하지만 함수 안에서는 arr가 포인터처럼 보이므로 sizeof(arr)로 전체 길이를 구할 수 없습니다.
void wrong_size(int arr[]) {
size_t n = sizeof(arr) / sizeof(arr[0]); // 잘못된 길이
}주의할 점
함수 매개변수에 int arr[10]처럼 숫자를 적어도 호출자에게서 길이가 자동 보장되지는 않습니다. 그 표기는 문서적 힌트에 가깝고, 실제 안전성은 길이 인자와 호출 규약에 달려 있습니다.
참고 링크
1 sources