0. 필요성
헤더에서 정의된 클래스를 메인 함수에 만들면 스택 메모리에 저장이 된다.
단, 동적 할당으로 만들면 힙 메모리에 저장이 된다.
// --Player.h--
#pragma once
class Player
{
public:
public:
int _hp;
int _atk;
};
// --Main.cpp--
#include <iostream>
#include <stdlib.h>
#include "Player.h"
using namespace std;
int main()
{
Player p1;
Player* p2 = new Player();
return 0;
}
여기서 player는 8바이트를 가지고 있다는 것을 알 수 있다(int 형 멤버 변수 2개를 들고 있음).
그렇다면 아래와 같이 다른 클래스의 객체를 들고 있는 player(Monster에 종속적임)는 몇 바이트를 들고 있을까?
#pragma once
#include "Monster.h"
class Player
{
public:
Monster _target;
public:
int _hp;
int _atk;
};
_target이 포인터 형(4바이트 또는 8바이트)이 아닌 객체 그 자체일 때는 직접 까보지 않는 이상 알 수 없다.
따라서 포인터 형으로 만들면 player가 몇 바이트인지 확실하게 알 수 있다.
#pragma once
// #include "Monster.h"
class Monster;
class Player
{
public:
Monster* _target;
public:
int _hp;
int _atk;
};
여기서 player는 int형 2개(8바이트), 포인터형 1개(8바이트)이므로 총 16바이트이다.
여기서 Player 클래스를 정의하기 전에 Monster를 먼저 선언하여 발생할 수 있는 오류를 미리 제거한다.
또는 다른 방법의 전방 선언도 있다.
#pragma once
// #include "Monster.h"
class Player
{
public:
class Monster* _target;
public:
int _hp;
int _atk;
};
1. 전방 선언을 할까, 헤더 파일을 포함할까?
그러나 Player 클래스 내에 몬스터를 처치하는 함수를 만들때 문제가 발생한다.
// --Player.cpp--
#include "Player.h"
void Player::KillMonster()
{
_target->_hp = 0;
}
몬스터 객체인 _target의 멤버 변수(_hp)에 접근할 수 없다. 따라서 몬스터의 헤더 파일을 포함해야한다.
#include "Player.h"
#include "Monster.h"
void Player::KillMonster()
{
_target->_hp = 0;
}
즉, 객체 내의 멤버 변수에 접근하고자 하면 반드시 포함 방법을 사용하여야 한다.
또는 객체 내에 있는 함수에 접근할 때도 포함 방법을 사용하여야 한다.
'기초 C++ 스터디 > 객체지향' 카테고리의 다른 글
8-2. 함수 포인터(2) (0) | 2023.06.08 |
---|---|
8-1. 함수 포인터(1) (0) | 2023.06.08 |
6-5. 캐스팅 (0) | 2023.06.02 |
6-4. 얕은 복사, 깊은 복사 (0) | 2023.06.01 |
6-3. 형(Type) 변환 : 포인터 (2) (0) | 2023.06.01 |