-
[JAVA] 가비지 컬렉터(Garbage Collector)프로그래밍/JAVA 2020. 7. 26. 02:06
객체의 소멸과 가비지
자바는 객체를 생성하는 new 연산자는 있지만 객체를 소멸시키는 연산자는 없음
=> 개발자가 마음대로 객체를 소멸시킬 수 없음
객체 소멸이란 new에 의해 생성된 객체 공간을 JVM(Java Virtual Machine)에게 돌려주어 가용 메모리에 포함시키는 것
C++과 다르게 delete 연산자, 소멸자가 존재하지 않음
=> 할당받은 메모리를 반환하는 코딩으로부터 자유로움
자바에서 new로 할당받은 후 사용하지 않게 된 객체 혹은 배열 메모리를 가비지라고 부름
JVM의 가비지 컬렉터(Garbage Collector)가 적절한 시점에 자동으로 가비지를 수집하여 가용 메모리에 반환
※ JVM : 운영체제의 메모리 영역에 접근하여 메모리를 관리하는 프로그램(메모리 관리, 가비지 컬렉션 수행)
/* 가비지 발생 예제 */ public class GarbageEx { public static void main(String[] args) { String a = new String("Good"); String b = new String("Bad"); String c = new String("Normal"); String d, e; a = null; d = c; c = null; } }
가비지 컬렉터(Garbage Collector)
동적으로 할당한 메모리 영역 중 사용하지 않는 영역을 탐지하여 해제하는 기능
※ Stack, Heap
Stack : 정적으로 할당한 메모리 영역
원시 타입의 데이터 값과 함께 할당, Heap영역에 생성된 Object 타입의 데이터 참조 값 할당
Heap : 동적으로 할당한 메모리 영역
모든 Object 타입의 데이터가 할당, Heap영역의 Object를 가리키는 참조 변수가 Stack에 할당
가비지 컬렉터 과정
1. 가비지 컬렉터가 Stack의 모든 변수를 스캔하면서 각각 어떤 객체를 참조하고 있는지 찾아서 마킹 - Mark
2. Reachable Object가 참조하고 있는 객체도 찾아서 마킹 - Mark
3. 마킹되지 않은 객체를 Heap에서 제거 - Sweep
=> Mark and Sweep
가비지 컬렉터 발생 시점
Eden
새로운 객체가 할당되는 영역
Eden 영역의 메모리가 전부 사용중인 경우 GC 발생(Minor)
=> Eden 영역에서 Mark and Sweep
S0(Survivor 0)
Eden 영역의 Reachable 객체가 S0 영역으로 옮겨짐
Eden 영역의 Unreachable 객체는 메모리에서 해제
S0 영역의 메모리가 전부 사용중인 경우 GC 발생(Minor)
=> S0 영역에서 Mark and Sweep
S1(Survivor 1)
S0 영역에 있던 객체는 S1 영역으로 이동
이동한 객체는 Age 값 증가
Eden 영역의 Reachable 객체가 S1 영역으로 옮겨짐
Eden 영역의 Unreachable 객체는 메모리에서 해제
S1 영역의 메모리가 전부 사용중인 경우 GC 발생(Minor)
=> S1 영역에서 Mark and Sweep
S0(Survivor 0)
S1 영역에 있던 객체는 S0 영역으로 이동
이동한 객체는 Age 값 증가
Eden 영역의 Reachable 객체가 S0 영역으로 옮겨짐
Eden 영역의 Unreachable 객체는 메모리에서 해제
S0 영역의 메모리가 전부 사용중인 경우 GC 발생(Minor)
=> S0 영역에서 Mark and Sweep
이러한 과정을 계속 반복
Old Generation
Age 값이 특정 값 이상이 되면 Old Generation 영역으로 이동
이 과정을 'Promotion' 이라고 함
Old Generation 영역이 모두 사용중인 경우 GC 발생(Major)
=> Old Generation 영역에서 Mark and Sweep
이러한 과정 역시 또한 반복
만약 Young(New) Generation 영역과 Old Generation 영역이 모두 사용중인 경우 GC 발생(Full)
=> 전체 영역에서 Mark and Sweep
※ S0 영역과 S1 영역 중 한쪽은 반드시 비어있음
Permanent Generation
JVM이 애플리케이션에서 사용하는 클래스 및 메소드를 설명하는 데 필요한 메타데이터를 포함
애플리케이션에서 사용 중인 클래스에 기반하여 런타임에 JVM에 의해 채워
Java SE 라이브러리 클래스 및 방법을 여기에 저장할 수 있음
GC의 관리영역이 아님
가비지 컬렉터 종류
Serial GC
GC를 처리하는 스레드가 1개
CPU 코어가 1개만 있을 때 사용하는 방식
Mark-Compact collection 알고리즘 사용
Parallel GC
GC를 처리하는 스레드가 여러개
Serial GC보다 빠르게 객체를 처리가능
Parallel GC는 메모리가 충분하고 코어의 개수가 많을 때 사용하면 좋음
Concurrent Mark Sweep GC(CMS GC)
stop-the-world 시간이 짧음
애플리케이션의 응답 시간이 빨라야 할 때 유용
다른 GC 방식보다 메모리와 CPU를 더 많이 사용
Compaction 단계가 제공되지 않음
G1 GC
각 영역을 Region 영역으로 나눔
GC가 일어날 때, 전체 영역(Eden, Survivor, Old generation)을 탐색하지 않음
바둑판 각 영역에 객체를 할당하고 GC를 실행
해당 영역이 꽉 차면 다른 빈 영역에 객체를 할당하고 GC 실행
stop-the-world 시간이 짧음
Compaction 단계를 제공
※ Stop-The-World
GC를 실행하기 위해 JVM이 애플리케이션 실행을 멈추는 것
stop-the-world가 발생하면 GC를 실행하는 스레드를 제외한 나머지 스레드는 모두 작업을 멈춤
GC 작업을 완료한 이후에 중단한 작업을 다시 시작
출처
http://www.yes24.com/Product/Goods/61269276
https://okky.kr/article/379036
https://medium.com/@recepinancc/til-12-garbage-collection-young-vs-old-generations-ab95b6a68653
https://www.youtube.com/watch?v=vZRmCbl871I
'프로그래밍 > JAVA' 카테고리의 다른 글
[JAVA] 상속 예제 (0) 2020.07.26 [JAVA] 접근지정자(Access Specfier) (0) 2020.07.26 [JAVA] 클래스와 객체 + 생성자 (0) 2020.07.26 [JAVA] JDK 설치 및 환경변수 설정 (0) 2019.12.16 [JAVA] length, length(), size() (0) 2019.08.08