728x90
자바의 메모리 영역
자바 프로그램을 실행 하게 되면 JVM은 OS(운영체제 ex. 윈도우, 유닉스, 리눅스) 로 부터 메모리를 할당 받습니다. 할당 받은 메모리를 용도에 따라서 여러 영역으로 나누어 관리합니다.
JVM의 메모리 공간(Runtime Data Area)은 크게 메서드(Method) 영역, 스택(Stack) 영역, 힙(Heap) 영역으로 구분되고 데이터 타입에 따라 각 영역에 나눠서 할당 되게 됩니다.
컴퓨터의 메모리는 한정된 공간이기 때문에 어떻게 관리하고 사용하느냐에 따라서 성능(속도)이 좌우됩니다. 따라서 Java 어플리케이션에서 메모리를 효율적으로 사용하기 위해서는 메모리 구조와 특징에 대해 이해할 필요가 있습니다.
1. 메서드 영역(Static or Method)
- JVM이 실행되고 클래스 로더를 통한 클래스 파일(.class)이 로딩될 때 생성됩니다.
- Class및 인터페이스 정보, Static 변수,Static 메서드, 메서드(Method), 생성자(constructor), 런타임 상수 풀 등을 저장하는 공간입니다.
- Method 영역에 있는 것은 어느곳에서나 접근이 가능합니다.
JVM 종료 시(프로그램 종료 시) 메모리에서 해제 됩니다. 즉, 프로그램 종료 전까지 메모리 상에 존재하게 됩니다. 그렇기 때문에 무분별하게 사용하게 되면 메모리 부족 현상이 일어날 수 있게 됩니다.
Method Area와 메모리 관리
Java 는 '동적 로딩'을 활용합니다. 즉, 모든 클래스가 프로그램 시작 시에 메모리에 로드되는 것이 아니라, 실제로 해당 클래스가 필요할 때 메모리에 로드됩니다. 이는 실행 시간(Runtime)에 필요한 클래스만 로드하여 효율적으로 메모리를 관리할 수 있게 합니다.
또한, 어떤 클래스의 인스턴스(객체)가 Heap 영역에 더 이상 존재하지 않고, 그 클래스에 대한 참조가 어디에도 없을 경우(ex. 모든 객체가 가비지 컬렉션에 의해 정리되고, 클래스 로더에 의한 참조도 없어진 경우), JVM은 해당 클래스의 메타데이터를 Method Area에서 삭제할 수 있습니다.
더보기
Java의 가비지 컬렉터는 주로 Heap 영역에서 사용되지 않는 객체를 정리합니다. 그러나 Metaspace(Java 8 이상) 에서도 가비지 컬렉션이 일어날 수 있습니다.
Runtime Constant Pool
런타임 상수 풀 영역은 클래스 로더가 메서드 영역에 클래스를 로딩할 때, 같이 메서드 영역에 적재되는 부분입니다. 즉, 클래스 별로 Constant Pool(Class file)을 가지고(컴파일 시 클래스 파일 내에 존재), 메서드 영역에 적재될 때 해당하는 Constant Pool(Class file)을 Runtime Constant Pool 에 올리게 됩니다. 따라서 Runtime Constant Pool에는 클래스 및 인터페이스의 상수 뿐만 아니라 메서드와 필드에 대한 모든 레퍼런스에 대한 정보를 가지고 있습니다.
2. 스택 영역(Stack)
- 기본 자료형(int, long, double, char, byte, boolean 등)에 해당되는 지역 변수, 매개변수의 데이터 값이 저장되는 공간입니다.
- 메서드가 호출되면 스택 영역에 독립적인 스택 프레임이 생성됩니다.
- Stack은 LIFO(Last-In-First-Out) 의 특징을 가지며, 스코프(Scope)의 범위를 벗어나면 스택 메모리에서 사라집니다.
스택 프레임(Stack Frame)
하나의 메서드에 필요한 메모리 덩어리를 묶어서 스택 프레임이라고 합니다.
하나의 메서드당 하나의 스택 프레임이 필요하며, 메서드를 호출하기 전 스택프레임을 자바 Stack영역 안에 생성한 후 메서드를 호출하게 됩니다.
스택 프레임에 쌓이는 데이터는 메서드의 매개변수(파라미터), 지역변수, 리턴값 등이 있습니다.
만일 메서드 호출 범위가 종료되면 스택에서 제거됩니다.
3. 힙 영역(Heap)
- 힙영역은 주로 객체와 같은 동적으로 할당된 데이터를 저장하기 위한 공간입니다. 자바에서는 'new' 키워드를 사용하여 객체를 생성할 때, 해당 객체는 힙 영역에 할당 됩니다.
- 참조형(Reference Type) 데이터 타입을 갖는 객체(인스턴스), 배열 등이 저장 되는 공간입니다.
- 단, Heap 영역에 있는 오브젝트들을 가리키는 레퍼런스 변수는 stack에 적재됩니다.
- Heap 영역은 Stack 영역과 다르게 보관되는 메모리가 호출이 끝나더라도 삭제되지 않고 유지 됩니다. 그러다 어떤 참조 변수도 Heap 영역에 있는 인스턴스를 참조하지 않게 된다면, 가비지 컬렉터에 의해 메모리에서 청소됩니다.
- Stack은 스레드 갯수마다 각각 생성되지만, heap은 몇개의 스레드가 존재하든 상관없이 단 하나의 heap영역만 존재합니다.
참고
'CS > Java' 카테고리의 다른 글
[Java] 추상클래스와 인터페이스의 차이 (0) | 2024.04.19 |
---|---|
[Java] 오버로딩(Overloading)과 오버라이딩(Overriding) 차이 (0) | 2024.04.14 |
[Java] 제네릭이란?(Generic) (0) | 2024.04.04 |
[Java] Garbage Collection(GC) 이란? (0) | 2024.03.01 |
[Java] Java 동작 과정 (0) | 2024.02.15 |