[JAVA] JVM 메모리 구조

임유빈·2022년 8월 1일

JAVA

목록 보기
2/17
post-thumbnail

1. JVM (Java Virtual Machine)

자바 프로그램 실행 단계

(1) 개념

JVM이란 Java Virtual Machine의 약자로, 자바 가상 머신이라고 부른다. 자바와 운영체제 사이에서 중개자 역할을 수행 하며, 자바가 운영체제에 구애 받지 않고 프로그램을 실행할 수 있도록 도와준다. 또한, 가비지 컬렉터로 메모리 관리도 자동으로 관리하며, 다른 하드웨어와 다르게 레지스터 기반이 아닌 스택 기반으로 동작한다.

자바 애플리케이션을 클래스 로더를 통해 읽어 들여 자바 API와 함께 실행하며 소스파일이 자바 컴파일러에 의해 바이트 코드로 변환 된다.

리터럴
컴파일 : 고급언어로 작성된 프로그램을 기계어로 번역하고 기계어 프로그램으로 고치는 과정
컴파일러 : 컴파일을 처리하는 프로그램

프로세스 : 단순히 실행 중인 프로그램을 지칭

  • 리터럴 : 소스 코드 내에서 직접 입력된 변수의 초기값
  • 스레드 : 프로세스 내에서 실제로 작업을 수행하는 주체, 모든 프로세스에는 한 개 이상의 스레드가 존재하여 작업을 수행함, 두 개 이상의 스레드를 가지는 프로세스를 멀티스레드 프로세스라고 함.
  • 데이터 타입 분류
    • 기본 타입 : 정수 타입, 실수 타입, 논리 타입
    • 참조 타입 : 배열 타입, 열거 타입, 클래스, 인터페이스

재정의와 재할당의 차이
런타임 - 프로그램 실행
컴파일 자바코드를 빌드할 때 컴파일을 통해서 바이트 코드르 바뀜

런타임, 컴파일

1. stack과 heap을 알기 전에

컴퓨터는 두가지 일을 한다. 연산 그리고 저장.
저장을 하려면 어떠한 형태가 필요한데 예시로 문자라는 형태로 글을 보관할 수 있다. 컴퓨터는 모든 데이터를 수의 형태로 저장한다. 그럼 그 수의 형태는 어떻게 저장될까?
2진수이다. 그게 바로 비트(0과 1 둘 중의 하나)이다.

(1) 주기억장치

우리가 부르는 메모리는 사실상 포괄적인 의미이다. 메모리는 캐시, 레지스터, 램을 모두 의미하지만 내가 보고자 하는 것은 주기억장치인 RAM이다. 메모리는 휘발성 형태의 데이터 저장소로, 시스템 전원이 꺼지면 메모리에 저장된 데이터도 사라진다.

(2) 보조기억장치

컴퓨터에는 보통 적어도 하나의 하드 디스크 드라이브가 있다. 하드디스크는 데이터와 프로그램을 영구적으로 저장하는 데 사용되며 보조기억장치이다.

(3) CPU

흔한 말로 CPU는 '컴퓨터의 뇌'라고 설명된다. 프로그램의 명령어를 해석하여 데이터를 연산 및 처리하고 실행해준다. 위의 설명들을 토대로 비유를 들어보자면

사람의 뇌
CPU = 사고를 담당하는 대뇌피질
RAM=단기기억을 담당
HDD(하드디스크)=장기기억을 담당

행동
CPU= 머릿속에 있는 기억을 떠올리는 행동
RAM=책장에 꽂혀 있는 책을 찾아 읽는 행동
HDD=지구 한 바퀴를 돌아서 특정한 내용을 찾아오는 행동이다.


2. 메모리 구조

(1) 코드(code) 영역

실행할 프로그램의 코드가 저장되는 영역으로 텍스트(code) 영역이라고도 부른다. 우리가 작성한 코드들이 들어간다고 생각하면 된다. 그리고 CPU는 코드 영역에 저장된 명령어를 하나씩 가져가서 처리하게 된다.

(2) 데이터(data) 영역

프로그램의 전역 변수와 정적(static) 변수가 저장되는 영역이다. 데이터 영역은 프로그램의 시작과 함께 할당되며, 프로그램이 종료되면 소멸된다.

(3) 스택(stack) 영역

함수의 호출과 관계되는 지역 변수와 매개변수가 저장되는 영역이다. 스택 영역은 함수의 호출과 함께 할당되며, 함수의 호출이 완료되면 소멸한다. 스택 영역은 푸시(push) 동작으로 데이터를 저장하고, 팝(pop) 동작으로 데이터를 인출한다. 이러한 스택은 후입선출(LIFO, Last-In First-Out) 방식에 따라 동작하므로, 가장 늦게 저장된 데이터가 가장 먼저 인출된다.

(4) 힙(heap) 영역

사용자가 직접 관리할 수 있는 '그리고 해야만 하는' 메모리 영역이다. 힙 영역은 사용자에 의해 메모리 공간이 동적으로 할당되고 해제된다.


3. stack과 heap

(1) 기본타입과 참조타입

단순하게 생각해보자. JAVA에서 stack 영역엔 기본타입, heap 영역엔 참조타입이다.
stack은 작은 값들을 heap은 큰 값들을 담는다고 생각한다.

변수 a와 b는 기본타입으로 값을 불러올 때 stack의 영역에서 바로 불러올 수 있다. 변수 k와 z는 참조타입으로 값은 heap 영역에 존재한다. 만약 변수 z의 값을 가져오고 싶다면?
stack 영역에서 변수 k의 주소를 찾고 heap에서 그 주소를 찾아 값을 받아오면 된다.

(2)

int[] arr = { 1, 2, 3, 4, 5 };         

System.out.println(arr);

// 결과물 : [해쉬코드]

위와 같은 경우 결과는 @주소가 나온다. [ ]은 참조변수이기 때문에 arr은 현재 stack에서 주소를 통해 heap에 있는 값을 가져와야 하기 때문이다. 그렇기에 for문이나 또는 Arrays.toString()메소드를 사용해주면 된다.

int[] arr = { 1, 2, 3, 4, 5 };

System.out.println(Arrays.toString(arr));

// 결과물 : [ 1, 2, 3, 4, 5 ];

0개의 댓글