static 변수와 static 중첩 클래스의 차이점

임원재·2024년 6월 23일
0

자바에서 클래스를 사용할 때 간혹 자료형 앞에 static을 붙여 static 변수static 메소드를 생성하는 경우가 있다. static을 사용하면 프로그램 실행 시 static영역에 선언되어 인스턴스를 생성하지 않고도 접근이 가능하다.

public class NestedOuterMain {

    public static int staticValue = 1;
    public int nonStaticValue = 1;

    public static void main(String[] args) {

        System.out.println(staticValue);
//        System.out.println(nonStaticValue); 에러 발생
    }
}

위 코드와 같이 staticValuestatic으로 선언되었기에 static 메모리에 할당된다. 해당 클래스의 인스턴스를 생성하지 않고도 참조 가능하다.
반면, nonStaticValue는 인스턴스를 생성하지 않았기에 접근이 불가능하다. 인스턴스를 생성해야 비로소 heap 메모리에 할당되어 접근 가능해진다.

정리하자면 인스턴스에 개수만큼 nonStaticValue가 생성되며 인스턴스 개수에 상관없이 딱 하나의 값만을 유지하는 변수가 static 변수이다.



예전에 중첩 클래스를 모르는 상태에서 중첩 클래스를 생성하는 상황이었다. 비슷한 기능을 하는 DTO클래스들을 생성하면서 이 클래스들을 비슷한 클래스끼리 묶어서 그룹화(혹은 계층화)하면 좀 더 깔끔하겠다라는 생각을 하였다. 이를 어떻게 해야할지 고민을 많이 하였다. 이를 인터페이스로 구현하기엔 메소드변수만 클래스에 존재했기에 인터페이스를 생성하는 의미는 없었다.

결국 클래스에서 인스턴스 변수를 가져오듯이(instance.value) 클래스 안에 클래스 여러개를 만들면 되지 않을까 라는 생각에 다다렀고 이를 다음과 같이 표현하였다.

class Outer {
	class Inner1 {
    	...
    }
    
    class Inner2 {
    	...
    }
}

이를 new Outer.Inner1()과 같이 생성하였지만 에러가 발생했다.

하지만 Intellij의 편리한 기능으로 alt + enter를 입력하여 에러를 해결했기에 왜 저 Inner1Inner2 클래스에 static이 왜 붙는지 알지 못한 채 그냥 넘어갔었던 경험이 있었다...



정적 중첩 클래스

정적 중첩 클래스는 외부 클래스와 전혀 다른 클래스이거나 클래스들을 묶어 그룹화를 할 때 사용되는 클래스이다. 외부 클래스와 연관이 없으므로 외부 클래스의 인스턴스를 생성할 때 인스턴스로 같이 따라오지 않는다. 다음과 같이 생성이 가능하다.

class Outer {
	static class Inner1 {
    	...
    }
    
    static class Inner2 {
    	...
    }
}

class앞에 static을 붙여 사용한다.
위에서 언급했듯이 원래 static의 의미는 해당 클래스의 인스턴스 생성에 관계없이 static 메모리에 딱 하나 할당하여 사용하기 위함이다. 정적 중첩 클래스는 외부 클래스 인스턴스 생성에 관계없이 사용 가능하므로 이런 점에는 기존의 static의 의미를 잘 사용한다. 하지만 차이점도 존재한다.

기존의 static은 클래스에 하나 존재했으나, 정적 중첩 클래스는 인스턴스를 여러번 생성 가능하다는 점이다.

static 변수 (혹은 메서드)static(정적) 중첩 클래스를 정리하자면 다음과 같다.

공통점

  • 외부 클래스의 인스턴스와 독립적 : 외부 클래스의 인스턴스를 생성하지 않고도 정적 중첩 클래스의 인스턴스를 생성할 수 있다.

차이점

  • 다중 인스턴스 가능 : static변수(혹은 메서드)는 클래스 당 하나 존재하지만 정적 중첩 클래스의 인스턴스는 여러 개 생성하여 독립적인 상태를 가질 수 있다.

0개의 댓글