[Java] 메모리 구조(static, stack,heap)

Brian·2021년 8월 17일
0

Java

목록 보기
5/6
post-thumbnail

프로그램을 구동하기 위해서 운영체제가 메모리(RAM)에 데이터 및 명령어를 저장할 공간을 할당해 준다. 메모리는 공간은 한정되어 있으며 컴퓨터에 있어 매우 중요한 자산이다. 이러한 것들을 어떻게 관리하는냐에 따라 성능이 좌우된다. 메모리를 효율적으로 사용하기 위해 메모리 구성과 특징에 대해 이해가 필요하다.

메모리를 효율적으로 쓴다는 것은 아직 멀고 먼 이야기이지만 그래도 알아둬야 좋은 부분이기에 끄적여 본다.

Static area

스태틱 메모리 영역에는 필드(field)에서 선언된 변수(전역변수) & 맴버변수(static이 붙은 자료형) static 영역에 데이터를 저장한다. Static 영역에 저장된 데이터는 프로그램이 종료 될때까지 메모리에 남아 있기 때문에 이 이유로 전역변수가 어디서든 사용이 가능 하다고 볼 수도 있다. 그 뜻은 전역변수를 많이 사용하게 되면 메모리 공간이 부족 할 수도 있다는 것이다.

Stack area

메소드 내에서 정의하는 기본 자료형에 해당되는 지역변수의 데이터의 값이 저장되는 공간이다. 메소드가 호출될 때 메모리가 할당되고 종료되면 메모리가 해제된다. int a = 10; 코드를 작성 하게 되면 메소드가 선언 될때 정수값이 할당 될 수 있는 메모리 공간 a라고 잡아두고 그 메모리 영역에 값이 10이 들어간다.

public class main{
	public static void main(String[] args){
    	int a = 3;
        a = 2;
        a = 1;
        System.out.println(a) // result : 1
        
        for(int i = 0; i<3; i++){
        }
        System.out.println(i); // compile error
    }
}

위 코드를 실행 해보면 a 변수에 여러 값을 넣어줬지만 1이 출력 되는 것을 확인 할 수 있다. 그 뜻은 이전 데이터는 사라지고 마지막이 남아 있다는 것을 알 수 있다. LIFO(Last In First Out).
For문 블록 밖에서 i 값을 출력 했을때 컴파일 에러가 발생한다. 그 이유는 i는 지역 변수이므로 for문이 종료되는 시점에 Stack 영역에서 해제되기 때문이다.

Heap area

new 키워드로 생성된 객체(인스턴스) & 참조형(Reference type)의 데이터 타입이 Heap 영역에 데이터가 저장된다. 힙 영역에 보관되는 메모리는 메소드 호출이 끝나도 사라지지 않고 유지된다. 힙 영역 메모리가 사라지는 시점은 Garbage Collector가 참조되지 않는 메모리를 확인하고 제거 할 시점이다. Stack 영역에 저장된 변수에는 실제 값이 저장된 Heap영역의 참조값(해시코드, 메모리 주소)을 가지고 있는것이다.

8가지 기본타입(byte, char, short, int, long, double, float, boolean)을 제외한 그 외의 타입은 참조변수라고 한다.
참조타입 (배열타입, 열거타입, 클래스, 인터페이스)

글만 봐서는 이해하기 어렵기 때문에 간단한 코드를 한 번 작성해 보겠다

public class main{
	public static void main(String[] args){
    	int[] a = null; //int 형 배열 선언 및 Stack 영역 공간 할당
        System.out.println(a); // result : null
        
        a = new int[3]; // Heap 영역에 공간 할당
        System.out.println(a) // result: @13bl9382 (참조값을 확인) 
    }
}

또 다른 간단한 예제로 두개의 new 연산자를 이용해서 두개의 변수가 같은 주소값을 가지고 있는지 아니면 다른지를 확인 해보는 것도 좋은 예시이다.

public class main{
	public static void main(String[] args){
    	String str1 = new String("apple");
        String str2 = new String("apple");
        
        if(str1 == str2) {
        	System.out.println("same memory address");
        } else {
        	System.out.println("different memory address"):
        }
    }
}

result : different memory address
new 연산자를 생성하면 데이터는 Heap 영역에 저장되고 str1, str2는 참조 값을 받게 된다. str1 과 str2가 같은 String을 생성하기 때문에 같은 주소 값을 가질거라고 생각 할 수 있지만 str1 & str2는 다른 참조값을 가진다.

StackHeap
Apple apple = 참조값;<-----------데이터

reference data!!! click👍

profile
Jiujitsu_coder

0개의 댓글