-
[C/C++ 강좌] 83강. 상속에서의 형변환 (2) - 다운캐스팅C++ 2022. 1. 20. 14:30
https://www.youtube.com/watch?v=ZGji0PxM1Y4&list=PLlJhQXcLQBJqywc5dweQ75GBRubzPxhAk&index=88
1. static_cast (정적형변환)
프로그래머의 실수로 상속관계의 클래스가 아닌 서로 전혀 관계없는 클래스끼리 형변환을 할 수도 있다.
#include <iostream> using namespace std; class Base { public: int a = 1; }; class Drv1 : public Base { public: void f() { cout << "Drv1::f()" << endl; cout << b << endl; } float b = 3.14; }; int main() { Base* b = new Drv1; int* a = new int(5); Drv1* d1 = (Drv1*)a; // 서로 관련없는 자료형끼리 캐스팅으로 프로그래머의 실수 d1->f(); delete b; }
위와 같은 코드는 실제로 구문오류는 뜨지않는다.
어처구니 없는 실수지만 코드가 길어지면 프로그래머가 이런 실수를 저지르지 말란 법은 없다.
이러한 실수를 막아주기위해 static_cast키워드를 사용하면된다.
Drv1* d1 = static_cast<Drv1*>(a);
이렇게 static_cast를 선언해주면 int형과 Drv1형은 서로 아무런 관련이 없기 때문에 구문오류가 발생한다.
Drv1* d1 = static_cast<Drv1*>(b); // 다운캐스팅이므로 허용!
그리고 위의 코드는 컴파일러에서 다운캐스팅이라고 생각하여 구문오류가 발생하지 않는다.
하지만 정적캐스트도 근본적으로 문제가 있다. 그것은 C++에서 막아놓은게 아닌 프로그래머가 조심해서 사용해야 한다는 것이다.
#include <iostream> using namespace std; class Base { public: int a = 1; }; class Drv1 : public Base { public: void f() { cout << "Drv1::f()" << endl; cout << b << endl; } float b = 3.14; }; class Drv2 : public Base { public: void f() { cout << "Drv2::f()" << endl; cout << c << endl; } int c = 3; }; int main() { Base* b = new Drv1; int* a = new int(5); Drv2* d2 = static_cast<Drv2*>(b); // 서로 관련없는 자료형끼리 캐스팅 d2->f(); delete b; }
새로운 Drv2클래스를 추가하였다.
만약 Base *b 포인터는 Drv1을 가리키고 있는데 b를 Drv2로 정적 캐스팅을 한다고하면 메모리 상에 이상하게 덮어 씌워져서 제대로 된 값을 얻기 힘들다.
이러한 점을 주의해서 써야한다는 것이 근본적인 문제점이며 이러한 문제점을 해결할 수 있는게 동적 캐스팅이다.
'C++' 카테고리의 다른 글
[C/C++ 강좌] 85강. 객체 지향 프로그래밍의 4대 원리 (1) (0) 2022.01.20 [C/C++ 강좌] 84강. 상속에서의 형변환 (3) - RTTI와 dynamic_cast (0) 2022.01.20 [C/C++ 강좌] 82강. 상속에서의 형변환 (1) - 업캐스팅 (0) 2022.01.20 [C/C++ 강좌] 81강. 생성/소멸자 실행 순서와 가상 소멸자 (0) 2022.01.19 [C/C++ 강좌] 80강. 순수 가상 함수와 추상 클래스 (0) 2022.01.19