728x90
오늘은 업 캐스팅 다운 캐스팅에 대해 공부하도록 하겠습니다.
캐스팅 이란?
캐스팅이란 타입을 변환하는 것을 의미합니다. C++는 상속관계에 있는 부모와 자식 클래스 간에는 서로 간의 형변환이 가능합니다.
업캐스팅
업캐스팅이란 자식 클래스의 객체가 부모 클래스 타입으로 형변환 하는 것을 말합니다.
아래의 코드에서 Human* h = s 이다 이 부분이 업 캐스팅 부분입니다. h가 student객체를 가르키지만 h는 Human타입이기 때문에 Human 클래스의 맴버에만 접근이 가능합니다.
#include<iostream>
using namespace std;
class Human
{
private:
int m_Age;
string m_BloodType;
string m_Gender;
public:
Human(int Age, string BloodType, string Gender) : m_Age(Age), m_BloodType(BloodType), m_Gender(Gender)
{
}
~Human()
{
}
virtual void print()
{
cout << m_Age << " " << m_BloodType << " " << m_Gender << endl;
}
};
class Student : public Human
{
private:
int m_Grade;
public:
Student(int Age, string BloodType, string Gender, int Grade) : Human(Age, BloodType, Gender), m_Grade(Grade)
{
}
~Student()
{
}
};
int main()
{
Student* s = new Student(20,"A","Male",1);
Human* h = s;
h->print();
return 0;
}
여기서 만약 Virtual을 걸어주면 Student에 print에 접근이 가능합니다 가상 함수 테이블에 의해
#include<iostream>
using namespace std;
class Human
{
protected:
int m_Age;
string m_BloodType;
string m_Gender;
public:
Human(int Age, string BloodType, string Gender) : m_Age(Age), m_BloodType(BloodType), m_Gender(Gender)
{
}
~Human()
{
}
virtual void print()
{
cout << m_Age << " " << m_BloodType << " " << m_Gender << endl;
}
};
class Student : public Human
{
private:
int m_Grade;
public:
Student(int Age, string BloodType, string Gender, int Grade) : Human(Age, BloodType, Gender), m_Grade(Grade)
{
}
~Student()
{
}
void print() override
{
cout << m_Age << " " << m_BloodType << " " << m_Gender<<" "<< m_Grade << " " << endl;
}
};
int main()
{
Student* s = new Student(20,"A","Male",1);
Human* h = s;
h->print();
return 0;
}
다운캐스팅
업캐스팅과 반대로 캐스팅 하는 것을 다운 캐스팅이라고 합니다. 업캐스팅된 것을 다시 원상태로 돌리는 것을 말하며 하위 클래스로 다운캐스팅을 할때는 타입을 명시적으로 지정해줘야 합니다.
#include<iostream>
using namespace std;
class Human
{
protected:
int m_Age;
string m_BloodType;
string m_Gender;
public:
Human(int Age, string BloodType, string Gender) : m_Age(Age), m_BloodType(BloodType), m_Gender(Gender)
{
}
~Human()
{
}
virtual void print()
{
cout << m_Age << " " << m_BloodType << " " << m_Gender << endl;
}
};
class Student : public Human
{
private:
int m_Grade;
public:
Student(int Age, string BloodType, string Gender, int Grade) : Human(Age, BloodType, Gender), m_Grade(Grade)
{
}
~Student()
{
}
void print() override
{
cout << m_Age << " " << m_BloodType << " " << m_Gender<<" "<< m_Grade << " " << endl;
}
};
int main()
{
Human* s = new Student(20,"A","Male",1);
Student* h = (Student*)s;
h->print();
return 0;
}
여기서 안전하게 캐스팅을 해볼려면 dynamic_cast를 하는 방법도 하나의 추천입니다. dynamic_cast는 RTTI에 의해 캐스팅을 해줌으로 부모 클래스 즉 베이스 클래스에 virtual함수가 꼭 있어야하며 실행중에 변환이 가능하며 만약 캐스팅 실패시 nullptr을 반환해줌으로 꼭 if로 체크를 해주시는것이 좋습니다.
#include<iostream>
using namespace std;
class Human
{
protected:
int m_Age;
string m_BloodType;
string m_Gender;
public:
Human(int Age, string BloodType, string Gender) : m_Age(Age), m_BloodType(BloodType), m_Gender(Gender)
{
}
~Human()
{
}
virtual void print()
{
cout << m_Age << " " << m_BloodType << " " << m_Gender << endl;
}
};
class Student : public Human
{
private:
int m_Grade;
public:
Student(int Age, string BloodType, string Gender, int Grade) : Human(Age, BloodType, Gender), m_Grade(Grade)
{
}
~Student()
{
}
void print() override
{
cout << m_Age << " " << m_BloodType << " " << m_Gender<<" "<< m_Grade << " " << endl;
}
};
int main()
{
Human* s = new Student(20,"A","Male",1);
Student* h = dynamic_cast<Student*>(s);
if (h != nullptr)
{
h->print();
}
return 0;
}
물론 static_cast또한 변환이 가능합니다. -> statc_cast는 컴파일중에 오류를 체크합니다.
'개발자 면접 공부 > C-C++' 카테고리의 다른 글
다익스트라 vs BFS (0) | 2022.08.11 |
---|---|
C++ RAII (0) | 2022.08.11 |
싱글톤 패턴(SingletonPattern) (0) | 2022.08.04 |
Struct vs Class (0) | 2022.08.03 |
(C++) 이동생성자(Move Constructor) (0) | 2022.08.02 |