[JAVA] Static

JHJeong·2024년 3월 27일
0

static 변수 : 자바에서 클래스 레벨에 선언되는 변수.

  • 특정 인스턴스에 속하지 않고, 클래스의 모든 인스턴스에 의해 공유된다.
  • 클래스 이름을 통해서 "static"변수에 직접 접근 할 수 있으며, 객체 인스턴스를 생성하지 않고 사용가능하다.
  • 프로그램이 실행되어 클래스가 메모리에 로드 될 때 생성되어 프로그램이 종료될 때까지 메모리에 남아있다는 것이 제일 중요한 특징이다.
  • 모든 인스턴스에서 공유해야할 때 유용하게 사용할 수 있지만, 객체지향 프로그래밍의 원칙과 상반될 수 있으므로, 남용하지 않는 것이 좋다.
  • 'static'변수는 JVM의 메소드 영역에 저장된다. 메소드 영역은 모든 스레드가 공유하는 메모리 영역으로, 클래스 데이터와 함께 static 변수도 이곳에 저장되어 클래스가 언로드될 때까지 유지된다.
public class TestStaticClass {
	static int staticCounter = 0;

	public TestStaticClass() {
		staticCounter++;
	}

	public static void main(String[] args) {
		new TestStaticClass();
		new TestStaticClass();
		new TestStaticClass();

		System.out.println( TestStaticClass.staticCounter );
	}
}

실행 결과
3

위 프로그램에서 보면 staticCounter 변수는 TestStaticClass클래스의 static 변수이기 때문에 모든 TestStaticClass 객체와 공유되고 있고, 따라서 TestStaticClass 의 생성자가 호출될 때 마다 staticCounter가 1씩 증가한다.
그리고 staticCounter 변수를 사용하기 위해서 TestStaticClass 클래스의 인스턴스를 생성할 필요가 없고, TestStaticClass 클래스 이름을 이용해서 직접 접근하여 출력하는 모습을 볼 수 있다.

static 메서드 : 클래스에 속한 메서드

  • 특정 인스턴스에 종속되지 않고, 클래스 레벨에서 호출됨
  • 객체를 생성하지 않고 사용할 수 있음
  • 클래스 이름을 통해 직접적으로 접근
  • static 메서드 내부에서는 인스턴스 변수나 인스턴스 메서드에 직접 접근 할 수 없으며, static 변수나 다른 static 메서드만 호출 가능
  • static 메소드는 오버라이딩 될 수 없음
    (그러나 하위 클래스에서 상위 클래스와 동일한 시그니처를 가진 static 메소드를 선언할 수는 있음. 이경우엔, 하위 클래스는 상위클래스의 static 메소드를 hide 한다고 하여 method hiding이라고 함)
  • 'static' 메소드 역시 JVM의 메소드 영역에 저장된다. static 메소드 호출 시 JVM은 메소드 영역에 저장된 해당 메소드의 코드를 실행한다.
class Calculator {
    // static 메서드 선언
    public static int add(int a, int b) {
        return a + b;
    }
    
    public static int subtract(int a, int b) {
        return a - b;
    }
}

public class TestCalculator {
    public static void main(String[] args) {
        // 객체 생성 없이 클래스 이름을 통해 static 메서드 호출
        int result1 = Calculator.add(5, 3);
        int result2 = Calculator.subtract(10, 4);
        
        System.out.println("5 + 3 = " + result1);
        System.out.println("10 - 4 = " + result2);
    }
}

실행 결과
5 + 3 = 8
10 - 4 = 6

위 프로그램에서 보면 Calculator 클래스에는 두 개의 static 메소드가 있는 걸 볼 수 있는데, 객체 생성없이 해당 메소드들을 사용하는 모습을 볼 수 있다.

static 블럭 : 클래스가 로딩될 때 최초 한 번 실행되는 코드 블록.

  • 주로 static 변수의 복잡한 초기화 과정에서 사용됨
    (예를 들어, 파일에서 데이터를 읽어와서 정적 변수를 초기화하거나, 조건에 따라 다른 값으로 초기화해야 하는 경우 등에 static 블록이 사용될 수 있다. )
  • 클래스가 JVM에 로드될 때 실행되며, 생성자와 달리 객체 생성 없이도 실행됨
  • static블록의 실행은 클래스 로더에 의해 클래스가 처음으로 참조될 때 발생하며, 클래스 당 단 한번만 실행된다.
  • 클래스가 JVM에 로드되고 클래스 변수가 메모리에 할당된 후, 생성자가 호출되기 전에 실행된다.
  • 여러 개의 static 블록이 있으면 작성한 순서대로 실행된다.
public class StaticBlockExample {
    // 정적 변수 선언
    static int[] numbers;

    // static 블록을 사용하여 numbers 배열 초기화
    static {
        numbers = new int[5];
        for (int i = 0; i < numbers.length; i++) {
            numbers[i] = (i + 1) * 2;
        }
    }

    public static void main(String[] args) {
        // 정적 변수 numbers에 접근하여 값 출력
        for (int num : numbers) {
            System.out.println(num);
        }
    }
}

출력결과.
2
4
6
8
10

위 소스에서 numbers 배열은 static 블록 내에서 초기화되고 있고, 이 블록은 StaticBlockExample 클래스가 처음 로드될 때 실행되어 numbers 배열을 초기화하고, main 메소드에서 이 배열의 값들을 출력한다.

profile
이것저것하고 싶은 개발자

0개의 댓글