728x90

가변 길이 배열(Variable-length Array)은 배열의 크기를 컴파일 타임에 정하지 않고 실행 타임에 정할 수 있도록 하는 기능이다.

TLDR;

  1. malloc은 메모리 수동 관리, VLA는 자동 관리
  2. C11에서는 지원이 필수가 아님 -> C++17에서도 지원이 필수가 아님
  3. VLA는 편리하지만 큰 크기의 배열을 사용할 때에 적합하지 않음

malloc과 VLA

C99 에서는 해당 기능을 제공한다.

int input_array_size(int size) {
  int array[size];

  ...

  return 0;
}

해당 기능을 지원하지 않는 C 버전을 사용할 때에는 아래와 같이 malloc을 이용해서 위 기능을 구현할 수 있지만, 그래도 위 기능을 직접 사용한다면 더욱 편리하게 구현할 수 있다.

int * array;
array = malloc(size * sizeof(int));

VLA를 무조건적으로 사용해야 할까?

서로 비슷해보이지만, malloc을 통해 통적 배열을 구현하는 것과 VLA를 사용하는 것은 정말 다르다.

  1. malloc을 통해 구현하는 것은 메모리를 수동으로 관리해야 한다. 해당 변수의 사용이 종료된다면 free를 이용해 해제해야 하며, 이를 잊어버리거나 메모리 해제를 여러 번 할 때 문제가 발생할 수 있다.
  2. VLA를 이용해 구현하는 것은 아무것도 해제할 필요가 없다는 장점이 있다.

위 차이점만 보면 VLA를 이용하는 방법만을 사용하면 된다고 느낄 수 있지만, 실상은 전혀 그렇지 않다.

malloc을 통해 생성된 배열은 힙 영역에 저장되는 반면, VLA를 이용해 생성된 배열은 보통 스택 영역에 할당된다. 일반적으로, 스택보다 힙에서 더 많은 메모리를 사용할 수 있어 크기가 큰 배열을 다룰 때에는 malloc을 이용하는 것이 좋다. VLA를 사용하는 것은 스택 오버플로우의 위험이 있다는 것을 알아야 한다.

그리고, 사용 가능한 범위에도 차이가 있는데, VLA 배열은 선언된 범위 내에서만 유효하지만, 동적 배열은 free를 호출할 때까지 프로그램의 모든 곳에서 사용할 수 있다.

VLA는 C99에서 지원한다. C89 버전에서는 지원하지 않으며, C11 버전에서는 VLA 지원이 필수가 아니다.

위 말은 C++17에서 C11이 부분집합으로 포함되기 대문에 컴파일러에 따라 지원 여부가 달라질 수 있다는 말이 된다.

 

 

728x90
728x90

'Advanced > C Trick' 카테고리의 다른 글

==과 =의 오타를 피하는 방법  (0) 2016.12.23
임시변수 없이 swap 구현하기  (0) 2016.12.22
do { ... } while(0) 을 사용하는 이유  (0) 2016.12.21