동적 메모리 관리 기법

1. 동적 메모리 할당의 필요성

프로그램 작성 시 사전에 메모리 크기를 정확히 알 수 없는 경우가 많습니다. 이러한 상황에서 고정된 크기의 배열이나 스택 메모리는 한계를 가집니다.


int val = 20; // 스택 영역에서 4바이트 공간 확보
char arr[10] = {0}; // 스택 영역에서 연속된 10바이트 공간 생성

위 예제처럼 정적인 메모리 할당은 다음과 같은 제약을 가지고 있습니다:

  • 공간 크기가 고정되어 동적으로 조정 불가
  • 배열 선언 시 길이 지정 필수, 이후 수정 불가

따라서 C 언어는 프로그램 실행 중 자유롭게 메모리를 할당하고 해제할 수 있도록 동적 메모리 관리 기능을 제공합니다.

2. 기본 동적 메모리 함수

2.1 memory_alloc 함수

C 표준 라이브러리에서는 다음과 같은 동적 메모리 할당 함수를 제공합니다:


void* memory_alloc(size_t size);

특징:

  • 요청한 크기만큼의 연속된 메모리 공간을 할당
  • 할당 성공 시 해당 공간 주소 반환, 실패 시 NULL 반환
  • 반환 타입은 void*, 사용자는 필요한 타입으로 변환 필요

2.2 memory_free 함수


void memory_free(void* ptr);

주의사항:

  • 동적으로 할당된 메모리만 해제 가능
  • NULL 포인터 전달 시 아무 작업도 수행하지 않음

3. 고급 메모리 관리

3.1 zeroed_memory_alloc 함수


void* zeroed_memory_alloc(size_t num, size_t size);

특징:

  • 지정된 개수와 크기의 메모리 공간을 할당하고 모든 바이트를 0으로 초기화
  • memory_alloc과 달리 자동으로 메모리를 클리어함

3.2 memory_resize 함수


void* memory_resize(void* ptr, size_t size);

특징:

  • 이미 할당된 메모리의 크기를 조정
  • 새로운 크기에 맞춰 데이터를 이동하거나 재배치
  • 실패 시 NULL 반환하므로 항상 결과 확인 필요

4. 안전한 메모리 관리 예제


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

int main() {
    int *data = (int*)memory_alloc(50 * sizeof(int));
    if (!data) return 1;

    // 새로운 크기로 리사이즈
    int* temp = (int*)memory_resize(data, 200 * sizeof(int));
    if (temp) {
        data = temp;
    } else {
        memory_free(data);
        return 1;
    }

    // 사용 후 메모리 해제
    memory_free(data);
    return 0;
}

5. 흔한 메모리 오류 사례

5.1 NULL 포인터 참조


void example() {
    int *ptr = (int *)memory_alloc(1000);
    if (!ptr) return;
    *ptr = 10; // NULL 체크 필수
    memory_free(ptr);
}

5.2 경계 초과 접근


void example() {
    int *arr = (int *)memory_alloc(10 * sizeof(int));
    for (int i = 0; i <= 10; i++) { // i=10일 때 범위 초과
        arr[i] = i;
    }
    memory_free(arr);
}

5.3 잘못된 메모리 해제


void example() {
    int value = 10;
    int *ptr = &value;
    memory_free(ptr); // 스택 메모리 해제 시도
}

6. 유연한 배열 멤버

C99부터 구조체의 마지막 멤버로 크기가不定인 배열을 정의할 수 있습니다.


struct DynamicArray {
    int length;
    int data[]; // 유연한 배열 멤버
};

int main() {
    struct DynamicArray *array = 
        (struct DynamicArray*)memory_alloc(sizeof(struct DynamicArray) + 100 * sizeof(int));
    array->length = 100;
    for (int i = 0; i < 100; i++) {
        array->data[i] = i;
    }
    memory_free(array);
    return 0;
}

태그: c-lang memory-management dynamic-allocation

6월 24일 18:23에 게시됨