C 언어의 동적 메모리 할당(Dynamic Memory Allocation)은 프로그램 실행 중에 필요한 만큼 메모리를 확보할 수 있게 해주는 강력한 기능입니다. 이 글에서는 동적 메모리 할당을 활용해 배열에 입력된 값들 중 최댓값과 최솟값을 찾는 방법을 예제 코드와 함께 자세히 알아보겠습니다.
문제 정의
목표는 동적 메모리 할당을 사용하여 배열 안에서 최댓값과 최솟값을 찾아 출력하는 C 프로그램을 작성하는 것입니다.
동적 메모리 할당이란?
동적 메모리 할당은 C 프로그래머가 런타임(실행 시점)에 메모리를 할당할 수 있도록 해주는 기능입니다. 컴파일 시점에 배열 크기를 미리 고정해 두지 않고, 사용자 입력에 따라 유연하게 메모리 크기를 결정할 수 있다는 점이 가장 큰 장점입니다.
런타임에 메모리를 동적으로 할당할 때 사용되는 대표적인 함수는 다음과 같습니다.
malloc() – 런타임에 지정한 바이트 크기만큼의 메모리 블록 하나를 할당합니다.
calloc() – 런타임에 연속된 여러 개의 메모리 블록을 할당하며, 모든 값을 0으로 초기화합니다.
realloc() – 이미 할당된 메모리의 크기를 줄이거나 늘릴 때 사용합니다.
free() – 더 이상 필요하지 않은 메모리 공간을 해제하여 시스템에 반환합니다.
배열에서 최댓값·최솟값 찾는 로직
1. 최댓값(max) 찾기 로직
먼저 malloc() 함수로 배열에 필요한 메모리를 동적으로 할당합니다. 이후 각 요소를 입력받으면서 현재까지의 최댓값과 비교하여, 더 큰 값이 나오면 최댓값을 갱신합니다.
p=(int*)malloc(n*sizeof(int)); // 동적 메모리 할당
for(i=0;i<n;i++){
scanf("%d",p+i);
if(*(p+i)>max) // 최댓값 탐색
max=*(p+i);
}
2. 최솟값(min) 찾기 로직
최솟값도 같은 원리로 구할 수 있습니다. 다만 초기값을 가능한 가장 큰 수로 설정해 두고, 입력된 값이 그보다 작을 때마다 최솟값을 갱신합니다.
for(i=0;i<n;i++){
scanf("%d",p+i);
if(*(p+i)<min) // 최솟값 탐색
min=*(p+i);
}
전체 예제 코드
#include<stdio.h>
#include<stdlib.h>
int main(){
int *p,n,i,max=-32768,min=32767;
printf("\n enter size:");
scanf("%d",&n);
p=(int*)malloc(n*sizeof(int)); // 동적 메모리 할당
printf("\n enter elements:");
for(i=0;i<n;i++){
scanf("%d",p+i);
if(*(p+i)>max) // 최댓값 탐색
max=*(p+i);
if(*(p+i)<min) // 최솟값 탐색
min=*(p+i);
}
printf("\n maximum=%d\n minimum=%d",max,min);
free(p); // 할당된 메모리 해제
}
실행 결과
enter size: enter elements: maximum=-32768 minimum=32767
위 실행 결과는 아무 요소도 입력되지 않았을 때의 출력 예시입니다. 이 경우 초기값인 max=-32768, min=32767이 그대로 화면에 표시됩니다.
코드 핵심 포인트 정리
max = -32768, min = 32767: int형이 표현할 수 있는 최솟값과 최댓값(16비트 환경 기준)으로 초기화하여, 어떤 값이 입력되더라도 올바르게 비교될 수 있도록 합니다.
p + i 포인터 연산: scanf에서 &p[i] 대신 p+i를 사용해도 동일하게 i번째 요소의 주소를 가리키므로 같은 결과를 얻습니다.
#include<stdlib.h>: malloc(), free() 함수를 사용하려면 stdlib.h 헤더 파일을 반드시 포함해야 합니다.
free(p) 호출: 동적으로 할당한 메모리는 사용이 끝난 후 반드시 free()로 해제해야 메모리 누수(memory leak)를 방지할 수 있습니다.