이 Step에서 다루는 것

  • 클래스와 객체(인스턴스)의 관계를 “설계도/실물”로 이해하기
  • 멤버 변수/멤버 함수가 메모리에 어떻게 배치되는지(데이터는 객체마다, 함수는 공유)
  • this 포인터가 무엇이고, 왜 멤버 함수가 “객체를 스스로 수정”할 수 있는지

학습 목표

  • “클래스는 메모리가 없고, 객체가 메모리를 가진다”를 설명할 수 있다.
  • 멤버 함수 호출이 내부적으로 함수(&객체, ...) 형태라는 감각을 가질 수 있다.
  • this가 무엇을 가리키는지(= 호출한 객체의 주소) 말로 설명할 수 있다.

클래스 = 설계도

  • class는 객체를 만들기 위한 설계도(타입 정의) 입니다.
  • class Knight { ... }; 자체는 “규칙”일 뿐, 그 순간엔 아직 k1 같은 실물이 없어서 메모리도 없다고 보면 됩니다.

클래스 → 객체 관계 비유

 [클래스 = 설계도/붕어빵 틀]                 [객체 = 인스턴스/붕어빵]

       ┌──────────────┐                    ┌──────────────┐
       │   Knight     │    "뿅" 찍어냄     │  k1 (객체1)  │
       │  - _hp       │  ───────────────►  │  hp: 100     │
       │  - _attack   │                    │  attack: 10  │
       │  - _defence  │                    └──────────────┘
       │  + Attack()  │                    ┌──────────────┐
       │  + HealMe()  │  ───────────────►  │  k2 (객체2)  │
       └──────────────┘                    │  hp: 80      │
        (메모리 없음)                       │  attack: 12  │
                                           └──────────────┘
                                            (스택/힙에 실제 할당)
구분클래스객체
개념설계도(타입)클래스 기반 실체(인스턴스)
메모리없음(규칙만)스택/힙에 할당됨
목적생성 규칙 정의실제 상태 보관 + 행동 수행

객체 = 인스턴스

  • 설계도를 이용해 실제 객체를 만든 것 = 인스턴스
  • Knight k1;k1은 “나이트 타입의 실물 객체”이며, 보통 스택에 생성됩니다.

멤버 변수 = 상태(데이터)

  • 객체가 가지는 데이터 = 멤버 변수
  • _hp, _attack, _defence
  • 전역 변수와 달리, 멤버 변수는 객체마다 따로 존재합니다.
    (k1의 _hp와 k2의 _hp는 서로 다른 값)

멤버 함수 = 행동(로직)

  • 객체가 수행할 행동 = 멤버 함수 (Attack(), HealMe(int), Die() 등)
  • 중요한 포인트:
    • 멤버 함수 코드는 “코드 영역”에 1번만 존재하고
    • 여러 객체가 같은 코드를 공유합니다.
    • 객체마다 다른 건 “멤버 변수(상태)”입니다.
class Player {
public:
    void Attack();
    void HealMe(int value);

    int _hp;
    int _attack;
    int _defence;
};

this 포인터

  • 멤버 함수에는 보통 숨겨진 포인터 this 가 전달됩니다.
  • this는 “현재 멤버 함수를 호출한 객체의 주소”입니다.
  • 그래서 _hp += value;는 내부적으로 this->_hp += value;처럼 동작합니다.

예: 생성자에서 이름 충돌이 날 때 this->가 특히 자주 보입니다.

class Knight {
public:
    Knight(int hp, int attack, int defence) {
        this->_hp = hp;
        this->_attack = attack;
        this->_defence = defence;
    }

private:
    int _hp;
    int _attack;
    int _defence;
};

참고: this는 “멤버 함수(비정적)”에서만 의미가 있습니다. (정적 함수엔 this가 없음)

객체 메모리 구조(감각 잡기)

  • 멤버 변수: 객체 생성마다 스택/힙에 개별 생성
  • 멤버 함수(코드): 코드 영역에 1개만 존재, 모든 객체가 공유

객체 메모리 배치(개념)

┌─────────────────────────────────────────────────────────────────────────────┐
│ [스택/힙 영역] (객체 데이터)                 [코드 영역] (함수 코드, 1번만)     │
├─────────────────────────────────────────────────────────────────────────────┤
│ k1: {_hp=100, _attack=10, _defence=2}  ──┐  Knight::Attack()                  │
│ k2: {_hp= 80, _attack=12, _defence=3}  ──┼─ Knight::HealMe(int)               │
│                                         └─ Knight::Die()                      │
└─────────────────────────────────────────────────────────────────────────────┘

this 포인터 동작 흐름(개념)

main()에서 호출:            Knight::HealMe(int value) 내부:

k1.HealMe(10);        ───►  this == &k1
                          this->_hp += value;

체크 질문 (스스로 답해보기)

  • 클래스와 객체 중 “실제로 메모리를 먹는 것”은 무엇일까?
  • k1.HealMe(10)k2.HealMe(10)이 같은 함수 코드를 쓰는데도 결과가 다른 이유는?
  • this는 무엇을 가리키며, 왜 멤버 함수에서 자연스럽게 멤버 변수를 수정할 수 있을까?

profile
李家네_공부방

0개의 댓글