기술스택/자바(Spring)

자바 Static 정적 메모리

ys.k 2025. 2. 2. 19:12

포스팅에 앞서 내용이 틀릴 수 있습니다.
해당 부분 지적 감사히 받습니다.

자바는 객체지향언어이다.

 

절차지향언어인 C언어와 다른 점은 모듈(객체)을 구성해 놓고 필요할 때 해당 모듈로 바로 접근해서 사용할 수 있기에 코드를 효율적으로 사용할 수 있다는 장점이 있다.

 

다만 해당 모듈을 사용하기 위해선 해당 모듈에 대한 인스턴스를 생성을 해야 한다.

 

인스턴스를 생성하면 해당 객체에 포함되어 있는 변수, 메소드를 그때 사용할 수 있게 된다.

 

또한 한 개의 객체에 대해 n개의 인스턴스를 생성할 수 있다.

 

예시 코드

class statictest{
    static int count1 = 0; // 클래스 변수
    int count2 = 0; // 인스턴트 변수
}

public class staticEx {
   
    public static void main(String[] args){

        statictest st1 = new statictest();
        statictest st2 = new statictest();

}

 

하지만 static 접근제어자를 사용하게 된다면, 해당 인스턴스를 생성하지 않더라도 접근할 수 있게 된다.

 

이유는 static은 객체 멤버가 아니라 Class 멤버이기 때문에, Class 로더가 Class를 로딩해서 메소드 메모리 영역에 적재할 때, 클래스 별로 관리가 된다. 따라서 클래스 로딩이 완료된 후에 바로 사용이 가능하다.

 

예시 코드

class statictest{
    static int count1 = 0; // 클래스 변수
    int count2 = 0; // 인스턴트 변수

    static void print1(){
        System.out.println("안녕하세요");
    }

    void print2(){
        System.out.println("반갑습니다");
    }
}

public class staticEx {
   
    public static void main(String[] args){

        statictest.print1();
    }

}

 

출력결과 : 안녕하세요

 

static키워드를 통해 생성된 필드, 메소드는 Heap이 아니라 Static영역에 할당되어 있다.

 

static영역에 할당된 메모리는 하나의 객체에서 파생된 n개의 인스턴스에서 공용으로 사용되며, 이는 따로 메모리 관리하는 영역에 데이터가 적재된 것이다.

 

자바에서는 Garbage Collector라는 것이 있는데, 이 static영역은 Garbage Collector의 영역 외에 존재하기에, 프로그램 종료 시까지 할당 메모리가 해제되지 않는다.

 

이는 효율 감소로 이어질 수 있기에 무분별한 사용은 지양하여야 한다.

 

예시 코드

class statictest{
    static int count1 = 0; // 클래스 변수
    int count2 = 0; // 인스턴트 변수
}

public class staticEx {
   
    public static void main(String[] args){

        statictest st1 = new statictest();
        statictest st2 = new statictest();
       
        st1.count1++;
        st1.count2++;

        System.out.println(st2.count1 + "::" + st2.count2);

       
    }

}

 

출력 결과 : 1::0

 

출력 결과에서 볼 수 있듯이, 인스턴스는 분리되어 있지만, static으로 선언된 필드의 값은 공유되는 것을 볼 수 있다.