JAVA :: 가비지 컬렉터(Garbage Collector)란
자바의 가비지 컬렉터(Garbage Collector) 즉, 쓰레기 수집 기능을 이해하려면 메모리에 대한 이해가 먼저다.
1. 자바 실행 프로그램인 JVM과 메모리
메모리는 OS가 관리하는데, 모든 프로그램들은 OS 위에서 돌아간다.
그리고 프로그램이 돌아가려면 당연 메모리가 있어야 한다.
때문에 프로그램들은 OS에게 "나 메모리좀 줘" 하고 요청을 한다.
자바의 실행 프로그램인 JVM도 예외는 아니다. 이 친구도 메모리가 필요하면 OS에게 요청해야한다.
메모리좀 달라고.
그런데 OS가 처음부터 자기가 가진 메모리 전부를 줘버리면, 다른 프로그램들에게 줄 메모리가 없게 된다.
때문에 각 프로그램에게 메모리의 일정부분만 빌려주는(?) 방식으로 관리가 된다.
<OS 메모리>
|
|
|
|
|||
A 프로그램 |
JVM |
B 프로그램 |
- |
이렇게 OS가 메모리를 각각의 프로그램에게 빌려주는 방식이다.
자. 그런데 JVM이 메모리를 쓰다가, OS가 준 메모리 용량이 턱없이 부족하다면?
JVM은 프로그램을 실행하다가, 메모리가 부족하면 OS에게 메모리를 더 달라고 요청한다.
그러면 OS가 또 JVM에게 메모리를 더 빌려준다.
|
|
|
| |||
A 프로그램 | JVM | B 프로그램 | JVM | - |
여기서 참고적으로 알아둘 것이 있다.
JVM은 또다시 그 안에서 변수, 함수 등 값이 저장될 메모리 주소를 할당해야 한다. OS로부터 받은 메모리들 중, 어디에다가 저장할지 그 주소를 할당해야 한다.
이 때,
JVM은 자기가 받은 메모리 안에서, 절대주소가 아니라 거기에 대한 '상대주소'를 할당한다. 이걸 offset 주소라고 한다.
0 ~ 100 | 101 ~ 200 | 201 ~ 300 | 301 ~ 400 | |||
A 프로그램 | JVM | B 프로그램 | JVM | - |
JVM이 받은 메모리의 절대 주소는 101 ~ 200, 301 ~ 400이지만, 이들의 상대적 주소는 0 ~ 200이라는 뜻이다.
이 말은 즉,
프로그램이 OS로부터 부여받은 메모리는 물리적으로는 분리되어 있을 수 있지만, 논리적으로는 하나의 메모리처럼 동작한다.
흠흠.
여기까지가 메모리에 대한 간단한 설명이었다.
자, 그럼 다시 돌아가서 Java의 가비지 컬렉터(Garbage Collector)의 '가비지'를 정의하고 가겠다.
2. 가비지(Garbage)란?
프로그램을 실행하다보면 '가비지'가 발생하게 된다.
요놈, 가비지는 '정리되지 않은 메모리', '유효하지 않은 메모리 주소'를 말한다.
대체 어느 경우인지 아래 코드로 가 봅시다.
int[] array = new int[3]; array[0] = 0; array[1] = 10; array[2] = 20; ... array = new String[] {'하하', '호호', '히히', '후후', '헤헤'}; System.out.println(array[0]);
1번째 라인에서 만들어진 array는 int타입의 3칸짜리 배열을 가리키는 주소이다.
3번째 코드부터 계속해서 이 array를 사용하다가
9번째 라인에서 새로운 String 타입의 배열을 만들어서 array가 새로 만든 배열을 가리키게 한다.
글탐, 기존에 array가 가리키고 있던 int타입의 3칸짜리 배열을 또 쓰려고 하면 어찌될까?
안타깝지만 방법이 없다 ㅠㅠ
주소를 잃어버려서 사용할 방법이 없다.
그리고 잃어버린 주소를 다시 찾을 방법도 없다.
요렇게 주소를 잃어버려서 사용할 수 없는 메모리가 바로 '정리되지 않은 메모리'이다.
이걸 프로그래밍 언어로는 "Dangling Object"라고 하고,
자바에서는 쓰레기, 즉 "가비지(Garbage)"라고 부른다.
*참고: 주소가 가리키는 메모리가 정리된 채로 있을 때, 그 주소는 더이상 유효하지 않게 된다.(없는 메모리 가리키는 주소라고)
이런 유효하지 않은 주소를 "Dangling Pointer"라고 부른다.(이건 C언어에 있음)
3. 가비지 컬렉터(Garbage Collector)란?
가비지에 대한 정의를 마쳤기 때문에, 가비지 컬렉터가 무엇인지는 쉽게 짐작할 수 있을 것이다.
가비지 컬렉터는 메모리가 부족할 때 쓰레기(가비지)를 정리해주는 프로그램을 말한다.
프로그램을 실행하다보면 가비지가 발생하게 되는데, 이놈들은 유효한 메모리가 아니다.
그렇게 되면 정리되지 않은 채로 남겨져있는 메모리들은 사용되지도 않으면서 자리를 차지하고 있게된다.
때문에 JVM의 가비지 컬렉터는 가비지를 다른 용도로 사용할 수 있게 '메모리 해제'를 시키는 프로그램이다.
4. 가비지 컬렉터는 언제 실행되는가?
JVM은 메모리를 부여받고 열심히 프로그램들을 실행하다가 메모리가 부족해지는 순간이 오면 OS에게 추가로 메모리를 더 요청하게 된다.
바로 이 메모리를 더 달라고 요청하는 때에 가비지 컬렉터(Garbage Collector)가 실행된다.
또, 서버 프로그램인 경우에는 24시간 내내 돌아가는데, 이 때에는 JVM이 한가할 때(idle time) 가비지 컬렉터가 실행된다.
(JVM이 종료되면, 당연히 사용하던 모든 메모리는 OS에게 반납된다.)
여기까지가 가비지 컬렉터에 대한 설명이었다.
자바 공부할 때, 가비지 컬렉터를 왜그렇게 열심히 설명하시나.. 그냥 자동으로 메모리 정리해주는 친구가 있다고 하면 될걸.
하고 생각했었는데,
C언어에서는 개발자가 강제로 메모리를 해제시키는 문법이 있다는걸 알게되면서 가비지 컬렉터의 위대함을 깨달았다.
* 참고: C언어에서는 개발자가 메모리 해제시키는 문법이 있지만, Java에는 없다.