일 | 월 | 화 | 수 | 목 | 금 | 토 |
---|---|---|---|---|---|---|
1 | 2 | |||||
3 | 4 | 5 | 6 | 7 | 8 | 9 |
10 | 11 | 12 | 13 | 14 | 15 | 16 |
17 | 18 | 19 | 20 | 21 | 22 | 23 |
24 | 25 | 26 | 27 | 28 | 29 | 30 |
Tags
- 컴퓨터구조
- spring webflux
- 네트워크
- Heap
- 자바
- JPA
- 알고리즘
- Kafka
- Spring
- OS
- Data Structure
- Algorithm
- 디자인 패턴
- Proxy
- MySQL
- redis
- Galera Cluster
- 백준
- IT
- mongoDB
- MSA
- c언어
- 파이썬
- 자료구조
- C
- Java
- design pattern
- 운영체제
- JavaScript
- react
Archives
- Today
- Total
시냅스
Java 참조 유형 과 GC (strong, soft, weak, phantom reference) 본문
참조 유형
자바에서는 명시적으로 메모리를 해제할 수 없습니다.
그러한 일들은 GC 가 대리 수행하고 있는데요.
https://liltdevs.tistory.com/161
어떠한 객체가 gc 의 대상이 되려면 스택 영역에서 참조하지 않아야 합니다.
gc 가 메모리를 관리를 대신해준다는 편의성과는 반대로
개발자가 메모리를 해제하고 싶을 때에도 해제할 수 없게 됩니다.
개발자는 이를 위해 아래에서 설명드릴 참조유형을 통해 관리할 수 있습니다.
참조 유형의 4단계
아래로 갈수록 참조가 약한 것으로, gc 의 대상이 되기 쉽습니다.
1. 강한 참조 Strong Reference
- 객체를 참조하는 일반적인 참조 유형입니다.
- 만약 객체가 Strong Reference 로 참조되고 있다면 해당 객체는 GC 대상이 되지 않습니다.
- 객체를 참조하는 모든 Strong Reference 가 해제될 때까지 객체는 메모리에 유지됩니다.
Object obj = new Object();
// 만약 GC 를 원한다면 명시적으로 null 표시를 해줘야 한다.
obj = null;
2. 약한 참조 Soft Reference
- Strong Reference 보다 약한 참조 유형입니다.
- 해당 객체를 참조는 Strong Reference 가 없고, 메모리가 부족한 경우 GC의 대상이 됩니다.
- java.lang.ref SoftReference class 를 사용하여 만들 수 있습니다.
- 참조지역성의 원리를 활용하기 위해 주로 cache 에 사용되며 Soft Reference 를 사용하여 메모리 부족 상황에서만 GC 의 대상이 되게 하여 캐시의 성능을 개선하면서 메모리 누수를 방지할 수 있게 됩니다.
Object obj = new Object();
SoftReference<Object> softRef = new SoftReference<>(obj);
obj = null;
System.gc();
// GC 가 여유롭다면 해시코드를 확인할 수 있다.
System.out.println(softRef.get());
3. 취약한 참조(…?) Weak Reference
- Soft Refence 보다 더 약한 참조 입니다.
- 해당 객체를 참조하는 Strong Reference 가 없는 경우 바로 가비지 컬렉션의 대상이 됩니다.
- java.lang.ref WeakReference class 로 만들 수 있습니다.
- 위에서 말한 캐시 관련 활용 또한 동일합니다.
- 다만 Weak Reference 는 GC가 여유 있어도 즉시 수거될 가능성이 높습니다.
Object obj = new Object();
WeakReference<Object> weakRef = new WeakReference<>(obj);
obj = null;
System.gc();
// 무조건 null 을 확인하게 된다.
System.out.println(weakRef.get());
4. 유령 참조 Phantom Reference
- 가장 약한 참조 유형입니다.
- 객체 수거시에도 참조가 남아있는 참조 유형입니다.
- 객체의 finalize() 메서드가 호출된 직후에 GC 에 의해 수거됩니다.
- java.lang.ref PhantomReference class 로 만들 수 있습니다.
- 생성자에는 넣고자 하는 클래스와 함께 ReferenceQueue 를 인자로 받습니다.
- PhantomReference 는 객체가 참조되지 않습니다.
- 객체의 finalize 메서드가 호출된 직후 Phantom Reference 가 ReferenceQueue 에 등록됩니다.
- 이를 통해 객체의 finalize() 메서드가 호출되었음을 알 수 있습니다.
- 일반적으로 Phantom Reference 는 Native 객체나 Direct Memory 와 같이 JVM 에서 관리되지 않는 자원들을 해제하기 위해 사용됩니다.
- Native 객체는 OS 의 메모리 영역에서 할당/관리 됩니다.
Object obj = new Object();
ReferenceQueue<Object> refQ = new ReferenceQueue<>();
PhantomReference<Object> phantom = new PhantomReference<>(obj, refQ);
obj = null;
// true
System.out.println(phantom.enqueue());
// null
System.out.println(phantom.get());
System.gc();
// false
System.out.println(phantom.enqueue());
// null
System.out.println(phantom.get());
'Java, Spring' 카테고리의 다른 글
HikariCP 101 : 코드로 알아보는 HikariCP (0) | 2023.04.01 |
---|---|
Java 로 구현하는 In-Memory Cache (2) | 2023.03.26 |
Java8 Parallel Stream 과 성능, 동시성 문제에 대해 (0) | 2023.03.25 |
코드로 뜯어보는 System.out.println 대신 logger 를 사용해야 하는 이유 (0) | 2023.03.19 |
Spring 예제로 보는 보안을 위한 HMAC (2) | 2023.03.11 |
Comments