프로그래밍 언어/Java

[자바의 정석] (Ch.6 객체지향개념) 클래스 변수, 인스턴스 변수

hyuga_ 2023. 9. 28. 12:44

클래스 변수와 인스턴스 변수

변수 정의

용어

  • 클래스 변수 (class variable, cv) = static 변수
  • 인스턴스 변수 (instance variable, iv)
  • 로컬 변수 (local variable, lv)

 

이렇게 카드가 있다고 하면, 속성에는 숫자, 무늬, 폭, 높이 등이 있을 것이다.

  • 이 중에서 숫자, 무늬는 각 카드 객체마다 달라야 한다.
  • 이처럼 개별 속성을 가져야 하는 것은 인스턴스 변수(iv)로 정의한다.
  • 카드 객체들의 폭, 높이는 모두 동일하게 유지되어야 한다.
  • 이처럼 공통 속성을 가지는 것은 클래스 변수(cv)로 정의한다.
  • 앞서 배웠듯, 클래스 변수는 iv와 똑같이 선언하는데 다만 앞에 static을 붙여주면 된다.
  • static = 정적인, 고정된

 

 

 

클래스 변수, 인스턴스 변수의 사용

class card {
    // iv
    String kind; // 무늬 
    int num; // 숫자 

    // cv
    static int width = 100; // 폭 
    static int height = 250; // 높이
}

위와 같이 정의된 class가 있다. 이를 활용하여 객체(인스턴스)를 사용해보자.

  1. 우선 인스턴스를 생성한다.
  2. 인스턴스를 사용한다.
    • 여기서 iv와 cv는 사용법이 다르다.

 

card c = new card(); // 참조변수 & 객체 생성

c.kind = "HEAR"; // iv -> 해당 인스턴스로 접근 (참조변수를 통해 접근)
c.number = 5; 

card.width = 200; // cv -> 클래스로 접근 (클래스 이름을 통해 접근) 
card.height = 300; 

cv는 참조변수가 아니라 클래스 이름을 직접 사용하여 접근한다.

  • 해당 인스턴스만을 위한 참조변수(여기서는 c)를 써도 작동이 되기는 한데, 이렇게 하면 iv와 헷갈려 오해를 일으킬 수 있다.
  • cv는 해당 클래스 전체적으로 다 통용되는 변수니까, 클래스 이름으로 접근하는 것이 더 가독성이 좋겠지?

 

또한 cv는 인스턴스를 필요로 하지 않으므로, 객체 생성 없이 바로 접근 및 사용 가능하다.

 

 

Card 클래스를 기반으로 두 개의 인스턴스(c1과 c2)를 생성했다.

이러한 과정을 수행할 때, 메모리에 실제로 어떤식으로 올라가는지를 형상화한 그림이다.

  • cv는 Method Area에 한 번만 생성된다. (클래스 정의된 부분 내부에 함께 정의)
  • 각 인스턴스는 Heap 영역에 생성된다.
  • iv는 인스턴스와 함께 저장된다.

 

 

자세한 내용은 아래 영상을 참고하자 (대략 10분쯤)

[자바의 정석 - 기초편] ch6-12,13 클래스변수 인스턴스변수

 

iv, cv 사용 실습

public class Ch6_class3 {
    public static void main(String[] args) {
    // 1. cv 사용
        System.out.println(card.height); // 250. cv는 객체 생성없이 바로 사용 가능!
        card.height = 300; // 마찬가지로 객체 생성없이 접근 및 수정도 가능 
        System.out.println(card.height); // 300

        // 2. 객체 생성 없이 iv 사용 시도 (에러)
//        System.out.println(card.num); // 에러 발생 (객체 생성 없이 iv 접근) 
//        (iv는 설계도(클래스)에 정의되어 있으나, 아직 실제로 생성되지는 않은 상태이다. 

        // 3. iv 사용
        card c1 = new card(); // 객체 생성. 이와 동시에 iv 2개(kind, num)도 생성된다. 
        card c2 = new card();

        c1.num = 10; // 서로 다른 인스턴스이므로
        c2.num = 5; // 각각 다른 값 저장 가능

        System.out.println(c1.num); // 10
        System.out.println(c2.num); // 5

        // 4. 참조변수를 통한 cv 사용 (권장하지 않음)
        c1.width = 30; // 참조변수를 통해서도 cv에 접근은 가능하다.
        System.out.println(card.width); // 30
        System.out.println(c1.width); // 30
        System.out.println(c2.width); // 30. cv가 바뀐 것이므로 같이 바뀌었다.
    }

}

// card 클래스 정의
class card {
    String kind; // 무늬 
    int num; // 숫자 

    static int width = 100;
    static int height = 250;
}