Namespaces
Variants

typeid operator

From cppreference.net
C++ language
General topics
Flow control
Conditional execution statements
Iteration statements (loops)
Jump statements
Functions
Function declaration
Lambda function expression
inline specifier
Dynamic exception specifications ( until C++17* )
noexcept specifier (C++11)
Exceptions
Namespaces
Types
Specifiers
constexpr (C++11)
consteval (C++20)
constinit (C++20)
Storage duration specifiers
Initialization
Expressions
Alternative representations
Literals
Boolean - Integer - Floating-point
Character - String - nullptr (C++11)
User-defined (C++11)
Utilities
Attributes (C++11)
Types
typedef declaration
Type alias declaration (C++11)
Casts
Memory allocation
Classes
Class-specific function properties
Special member functions
Templates
Miscellaneous

타입의 정보를 조회합니다.

dynamic type 을 알아야 하는 경우와 polymorphic object 의 정적 타입 식별을 위해 사용됩니다.

목차

구문

typeid ( type ) (1)
typeid ( expression ) (2)

typeid 표현식은 lvalue 표현식 으로서, 정적 저장 기간 을 가지며, 다형적 타입 std::type_info 또는 이로부터 파생된 어떤 타입의 const 한정 버전인 객체를 참조합니다.

표준 라이브러리의 std::type_info 정의가 typeid 사용 시 보이지 않으면, 프로그램은 형식이 잘못되었습니다.

설명

만약 type 또는 expression 의 타입이 클래스 타입이거나 클래스 타입에 대한 참조인 경우, 해당 클래스 타입은 incomplete type 일 수 없습니다.

1) type 을 나타내는 std::type_info 객체를 참조합니다. type 이 참조 타입인 경우, 결과는 참조된 타입의 cv-unqualified 버전을 나타내는 std::type_info 객체를 참조합니다.
2) 다음 expression 을 검사합니다 :
  • 그렇지 않은 경우, typeid 표현식을 평가하지 않으며 , 이 식별자가 나타내는 std::type_info 객체는 표현식의 정적 타입을 나타냅니다. Lvalue-to-rvalue, array-to-pointer, 또는 function-to-pointer 변환이 수행되지 않습니다.
  • 그러나 prvalue 인수에 대해서는 (형식적으로) 임시 객체 구체화 가 수행됩니다: 인수는 typeid 표현식이 나타나는 컨텍스트에서 파괴 가능해야 합니다.
(C++17 이후)

만약 type 또는 expression 의 타입이 cv-qualified인 경우, typeid 의 결과는 cv-unqualified 타입을 나타내는 std::type_info 객체를 참조합니다 (즉, typeid ( const T ) == typeid ( T ) ).

만약 typeid 가 생성 중이거나 소멸 중인 객체(소멸자나 생성자 내부, 생성자의 initializer list 또는 default member initializers 에서)에 사용되면, 이 typeid 가 참조하는 std::type_info 객체는 가장 파생된 클래스가 아닌 경우에도 현재 생성 중이거나 소멸 중인 클래스를 나타냅니다.

  1. 다른 상황에서, 이러한 expression 을 평가하는 것은 정의되지 않은 동작을 초래합니다.

참고 사항

다형성 타입의 표현식에 적용될 때, typeid 표현식의 평가는 런타임 오버헤드(가상 테이블 조회)를 수반할 수 있으며, 그렇지 않은 경우 typeid 표현식은 컴파일 타임에 해결됩니다.

typeid 가 참조하는 객체의 소멸자가 프로그램 종료 시점에 실행되는지 여부는 명시되어 있지 않습니다.

동일한 타입에 대한 typeid 표현식의 모든 평가가 동일한 std::type_info 객체를 참조한다는 보장은 없지만, 이들은 동등하게 비교될 것이며, 이러한 type_info 객체들의 std::type_info::hash_code 는 동일할 것이며, 그들의 std::type_index 도 마찬가지일 것입니다.

const std::type_info& ti1 = typeid(A);
const std::type_info& ti2 = typeid(A);
assert(&ti1 == &ti2); // 보장되지 않음
assert(ti1 == ti2); // 보장됨
assert(ti1.hash_code() == ti2.hash_code()); // 보장됨
assert(std::type_index(ti1) == std::type_index(ti2)); // 보장됨

키워드

typeid

예제

이 예제는 type_info::name 이 전체 타입 이름을 반환하는 구현 중 하나를 사용한 출력을 보여줍니다; gcc나 유사한 컴파일러를 사용하는 경우 c++filt -t로 필터링하십시오.

#include <iostream>
#include <string>
#include <typeinfo>
struct Base {}; // non-polymorphic
struct Derived : Base {};
struct Base2 { virtual void foo() {} }; // polymorphic
struct Derived2 : Base2 {};
int main()
{
    int myint = 50;
    std::string mystr = "string";
    double *mydoubleptr = nullptr;
    std::cout << "myint has type: " << typeid(myint).name() << '\n'
              << "mystr has type: " << typeid(mystr).name() << '\n'
              << "mydoubleptr has type: " << typeid(mydoubleptr).name() << '\n';
    // std::cout << myint is a glvalue expression of polymorphic type; it is evaluated
    const std::type_info& r1 = typeid(std::cout << myint); // side-effect: prints 50
    std::cout << '\n' << "std::cout<<myint has type : " << r1.name() << '\n';
    // std::printf() is not a glvalue expression of polymorphic type; NOT evaluated
    const std::type_info& r2 = typeid(std::printf("%d\n", myint));
    std::cout << "printf(\"%d\\n\",myint) has type : " << r2.name() << '\n';
    // Non-polymorphic lvalue is a static type
    Derived d1;
    Base& b1 = d1;
    std::cout << "reference to non-polymorphic base: " << typeid(b1).name() << '\n';
    Derived2 d2;
    Base2& b2 = d2;
    std::cout << "reference to polymorphic base: " << typeid(b2).name() << '\n';
    try
    {
        // dereferencing a null pointer: okay for a non-polymorphic expression
        std::cout << "mydoubleptr points to " << typeid(*mydoubleptr).name() << '\n'; 
        // dereferencing a null pointer: not okay for a polymorphic lvalue
        Derived2* bad_ptr = nullptr;
        std::cout << "bad_ptr points to... ";
        std::cout << typeid(*bad_ptr).name() << '\n';
    }
    catch (const std::bad_typeid& e)
    {
        std::cout << " caught " << e.what() << '\n';
    }
}

가능한 출력:

======== output from Clang ========
myint has type: i
mystr has type: NSt3__112basic_stringIcNS_11char_traitsIcEENS_9allocatorIcEEEE
mydoubleptr has type: Pd
50
std::cout<<myint has type : NSt3__113basic_ostreamIcNS_11char_traitsIcEEEE
printf("%d\n",myint) has type : i
reference to non-polymorphic base: 4Base
reference to polymorphic base: 8Derived2
mydoubleptr points to d
bad_ptr points to...  caught std::bad_typeid
======== output from MSVC ========
myint has type: int
mystr has type: class std::basic_string<char,struct std::char_traits<char>,⮠
class std::allocator<char> >
mydoubleptr has type: double * __ptr64
50
std::cout<<myint has type : class std::basic_ostream<char,struct std::char_traits<char> >
printf("%d\n",myint) has type : int
reference to non-polymorphic base: struct Base
reference to polymorphic base: struct Derived2
mydoubleptr points to double
bad_ptr points to...  caught Attempted a typeid of nullptr pointer!

결함 보고서

다음의 동작 변경 결함 보고서들은 이전에 발표된 C++ 표준에 소급 적용되었습니다.

DR 적용 대상 게시된 동작 올바른 동작
CWG 492 C++98 typeid 가 cv-qualified 참조에 적용될 때,
결과가 참조된 타입을 나타냄
결과가 cv-unqualified 참조된 타입을
나타냄
CWG 1416 C++98 최상위 cv-qualification에 관한 문구가
오해될 수 있었음
문구를 개선함
CWG 1431 C++98 typeid std::bad_typeid 만 throw할 수 있었음 매치 가능한 파생 클래스들을
throw할 수 있도록 허용
CWG 1954 C++98 널 포인터 역참조가 expression 의 하위 표현식에서
검사될 수 있는지 불명확했음
최상위 레벨에서만 검사함

참고 항목

일부 타입의 정보를 포함하며, typeid 연산자가 반환하는 클래스
(class)