[JS] 메모리 관리 - 가비지 콜렉션(GC)

임찬혁·2023년 3월 28일
1

JavaScript

목록 보기
5/5
post-thumbnail

C, C++ 등 저수준 언어에서는 메모리 관리를 위해 malloc, calloc, realloc, free 등의 함수를 지원합니다. 하지만 JavaScript 에서는 자동으로 메모리를 할당하고 해제해주는데, 이는 가비지 콜렉션(GC) 에 의해 관리됩니다.
이번 포스트에서는 JavaScript 에서 메모리 관리를 해주는 GC 에 대해 알아보겠습니다.

메모리 생존주기 (Lifecycle)

모든 프로그래밍 언어에서의 메모리 생존주기는 비슷합니다.

  1. 필요시 메모리가 할당됩니다.
  2. 해당 메모리 값을 쓰거나 읽습니다.
  3. 필요가 없어지면 메모리를 해제합니다.

2번은 모든 언어에서 명시적이지만, 1번과 3번은 C 같은 저수준 언어에서는 명시적이고 JavaScript 같은 고수준 언어에서는 암묵적으로 작동합니다.

메모리 할당

JavaScript 에서는 변수함수 등을 선언할 때 메모리가 자동으로 할당됩니다.

let num = 7;  // 숫자 변수 선언

let str = 'value';  // 문자열 변수 선언

const date = new Date();  // Date 객체 변수 선언

const obj = {  // 객체 변수 선언
  key: 'value',
};

function func(param) {  // 함수 선언
  return param;
}

메모리 사용

메모리 사용은 할당된 메모리의 값을 읽거나 쓰는 동작을 의미합니다. 또한 함수를 호출하는 것도 메모리를 사용하는 것입니다.

console.log(obj.key);  // obj 객체의 key 속성 읽기

str = func('new value');  // func 함수를 호출한 결과값을 str 변수에 넣기

메모리 해제

메모리가 더이상 사용되지 않는 경우에는 메모리를 해제하게 됩니다. 하지만 JavaScript 에서는 메모리를 개발자가 명시적으로 해제할 수 있는 방법이 없기 때문에 GC 가 해당 작업을 수행해주고 있습니다.

JavaScriptGC표시하고 쓸기(Mark-and-Sweep) 알고리즘을 사용하고 있습니다. 이 알고리즘은 메모리에 닿을 수 있는(Reachable) 지 체크하고, 만약 닿을 수 없다 면 메모리 해제의 대상이 됩니다.
이 알고리즘은 roots(전역변수들의 모음) 라는 집합을 가지고 있고, roots 에서 참조할 수 있는 메모리는 닿을 수 있는 메모리로 인지합니다.

let toy = {
  price: '$30',
  color: 'blue',
};

toy 라는 변수pricecolor 속성을 가진 객체 의 참조값을 저장합니다.
이 때 객체 가 저장되어 있는 메모리는 toy 라는 변수로 접근할 수 있기 때문에 닿을 수 있는 메모리가 됩니다.

toy = null;

하지만 이렇게 toy 변수에 null 을 할당하게 되면 객체 에 접근할 수 있는 경로가 사라졌기 때문에 해당 메모리는 닿을 수 없는 메모리가 되고, GC 의 대상이 됩니다.

메모리에 이중으로 참조하는 경우에는 어떻게 될까요?

let toy = {
  price: '$30',
  color: 'blue',
};
let stuff = toy;

toy = null;

이 경우에는 객체 에 접근할 수 있는 방법이 stuff 가 남아있기 때문에 GC 이 대상이 되지 않습니다.

표시하고 쓸기 (Mark-and-Sweep) 알고리즘

JavaScript 에서 채택한 GC 알고리즘인 표시하고 쓸기(Mark-and-Sweep) 알고리즘이 어떻게 동작하는지 알아보겠습니다.

메모리 참조 트리가 위와 같이 되어있다고 가정해보겠습니다. GCroots 부터 시작해서 연결되어있는 노드들을 방문합니다. 방문한 노드는 mark 를 해두면서 완전탐색 과정을 거칩니다.

탐색을 마친 뒤에 mark 가 되어있지 않은 노드들을 메모리에서 해제합니다.

이런 방식으로 동작하기 때문에 알고리즘 이름이 Mark-and-Sweep 입니다.

마치며

메모리 관리를 자동으로 해준다고 해서 GC 가 만능은 아닙니다. 이런 내용을 모르는 채로 개발을 하다보면 언젠간 메모리가 터지는 경우가 생길 수도 있고, 최적화를 하기 힘듭니다. 가능한 메모리 관리도 신경쓰며 개발하는 습관을 들이면 좋겠습니다.

profile
개발새발자

0개의 댓글