본문으로 이동
메뉴 여닫기
환경 설정 메뉴 여닫기
개인 메뉴 여닫기
로그인하지 않음
지금 편집한다면 당신의 IP 주소가 공개될 수 있습니다.

자바의 static 은 필드나 메소드를 개별 객체가 아니라 클래스 자체에 소속시키는 키워드다. static 이 붙은 멤버는 객체를 생성하지 않고 클래스 이름만으로 사용할 수 있다.

자바에서 일반적인 필드와 메소드는 객체(인스턴스)마다 따로 존재하므로 `new` 로 객체를 만든 뒤에야 쓸 수 있다. 반면 static 멤버는 클래스가 메모리에 올라갈 때 한 번만 만들어지고 모든 객체가 그 하나를 공유한다. 따라서 객체 생성 없이 `클래스명.멤버명` 형태로 접근한다.

static 이 붙은 메소드를 정적 메소드 또는 클래스 메소드라고 한다.

public class Test {
    public static void main(String[] args) {
        System.out.print(Test.check(1));
    }
    static String check(int num) {
        return (num >= 0) ? "positive" : "negative";
    }
}

위에서 `check` 는 static 이므로 `Test` 객체를 만들지 않고 `Test.check(1)` 로 바로 호출한다. `main` 메소드가 static 인 것도 같은 이유다. 프로그램 시작 시점에는 아직 아무 객체도 없으므로 JVM 이 객체 없이 호출할 수 있어야 한다.

  • 정적 메소드 안에서는 인스턴스 필드와 인스턴스 메소드를 직접 쓸 수 없다. 어느 객체의 것인지 정해지지 않았기 때문이다.
  • 같은 이유로 `this` 와 `super` 를 쓸 수 없다.
  • 인스턴스 메소드에서 정적 멤버를 쓰는 것은 반대로 아무 문제가 없다.
  • 정적 메소드는 오버라이딩 되지 않는다. 하위 클래스에 같은 이름을 선언하면 재정의가 아니라 가리기(hiding)가 되며, 호출될 메소드는 실행 시점의 객체 타입이 아니라 컴파일 시점의 참조 타입으로 결정된다.
public class Counter {
    static int count = 0;
    Counter() { count++; }
}

`count` 는 모든 `Counter` 객체가 공유하므로 생성된 객체의 총 개수를 셀 수 있다. 공유 상태이므로 여러 스레드가 동시에 건드리면 동기화가 필요하다.

정적 초기화 블록

편집 원본 편집
static {
    // 클래스가 처음 로딩될 때 한 번만 실행된다
}

정적 필드를 복잡한 절차로 초기화해야 할 때 쓴다. 클래스 로딩 시 한 번만 실행된다.

인스턴스 멤버와의 비교

편집 원본 편집
구분 static 멤버 인스턴스 멤버
소속 클래스 객체
생성 시점 클래스 로딩 시 객체 생성 시
개수 하나 객체마다 하나씩
접근 방법 클래스명.멤버명 참조변수.멤버명
this 사용 불가 가능