• 카테고리

    질문 & 답변
  • 세부 분야

    프로그래밍 언어

  • 해결 여부

    미해결

typeid( ref.getThis( ) ) 호출시 getThis( ) 내부 출력함수가 작동하지 않는 이유

21.12.28 13:16 작성 조회수 180

2

7분 16초부터 교수님께서 getThis( ) 함수 내부에 함수명 출력을 구현하셨습니다. 

type( ref.getThis() ) 호출시에도 함수 내부에 구현된 함수명 출력이 실행되어야 하는데 무시되네요. 직접 구현하여도 마찬가지입니다.

#include <iostream>
#include <typeinfo>
using namespace std;

class A {
public:
    void NotVirtual() { cout << "A" << endl; }
    virtual A* getThis() {
        cout << __FUNCTION__ << " A is working " << endl;
        return this;
    }
};

class B: public A {
public:
    void NotVirtual() { cout << "B" << endl; }
    virtual B* getThis() override { 
        cout << __FUNCTION__ << " B is working " << endl;
        return this; 
    }
};

int main() {
    B b;

    A& ref = b;
    cout << typeid(ref.getThis()).name() << endl;
    typeid(ref.getThis()).name();
    ref.getThis();
}

 

출력값은 다음과 같습니다. getThis( ) 함수가 세 번 실행되었는데도 출력값은 한 번만 나옵니다. 

typeid 내부에서 신기한일이 일어나는거 같습니다. 뭐라고 검색해야 해당 내용을 알 수 있을지 모르겠어요! 혹시 도움을 구할 수 있나요. 왜 getThis( ) 가 typeid와 함께 사용될 때 내부 출력이 무시되는지 궁금합니다. 

답변 1

답변을 작성해보세요.

3

강민철님의 프로필

강민철

2021.12.29

안녕하세요 ^^

typeid가 포함되어 있는 코드의 경우, 즉 typeid(b.getThis()).name() 에서 

getThis()의 리턴값의 타입이 void이기 때문에,

질문자님의 말씀대로 '무시'한 것이 아닌 아무것도 표기되지 않은 것입니다. 

 

예를 들어, 리턴값이 int인 함수를 typeid에 넣은 아래의 예시 코드를 보면

int라는 결과가 잘 뜨는 것을 알 수 있습니다.

 

#include <iostream>
using namespace std;

class A
{
public:
	void print() { cout << "A" << endl; }
	virtual A* getThis()
	{ 
		cout << "A::getThis()" << endl;
		return this; 
	}
	int hello() {
		return 1;
	}
};

class B : public A
{
public:
	void print() { cout << "B" << endl; }
	virtual B* getThis()
	{
		cout << "B::getThis()" << endl;
		return this;
	}
	int hello() {
		return 1;
	}
};

int main() 
{
	A a;
	B b;

	A &ref = b;

	b.getThis()->print(); 
	ref.getThis()->print(); 
	cout << typeid(b.hello()).name() << endl; 
	cout << typeid(ref.hello()).name() << endl;

	return 0;
}

 

실행 결과

---

B::getThis()

B

B::getThis()

A

int

int

 

왜 typeid가 getThis 함수의 리턴값 타입만을 반환했는지 보다 자세히 이해하려면 아래 링크 속 typeid의 내부 동작을 읽어보시면 됩니다. 

https://en.cppreference.com/w/cpp/language/typeid

typeid는 인자가 다형성 타입일 경우에만 실행하고, 그렇지 않은 경우에는 정적인 타입만을 반환한다고 나와 있습니다.

"If expression is not a glvalue expression of polymorphic type, typeid does not evaluate the expression, and the std::type_info object it identifies represents the static type of the expression."

 

아래 예제를 보세요 (위 링크의 예제를 일부 발췌했습니다.)

 

#include <iostream>

int main() {
	int myint = 50;

	// std::cout << myint is a glvalue expression of polymorphic type; it is evaluated
	std::cout << typeid(std::cout << myint).name() << '\n';

	// std::printf() is not a glvalue expression of polymorphic type; NOT evaluated
	std::cout << typeid(std::printf("%d\n", myint)).name() << '\n';

}

 

위 예제를 실행하면 

typeid(std::cout << myint).name() 은 std::cout << myint 가 실행되어 50이 출력되고, 그 다음 타입이 반환되지만

std::printf("%d\n", myint)은 실행되지 않고 정적인 타입(int) 만 반환되는 것을 알 수 있습니다.

정리하면, 질문자님의 코드의 경우, typeid는 getThis()의 리턴값 타입을 반환했고, 해당 리턴값의 형은 void입니다. 

 

질문자님의 질문과 같은 질문은 아래 링크에서 확인해보실 수 있습니다.

 

https://stackoverflow.com/questions/33402414/is-function-not-called-inside-typeid

 

감사합니다.