У меня возникли проблемы с пониманием соответствия между типом возвращаемого значения typeid
и актуально type_info
объекты, которые, кажется, работают не так, как обычные объекты. Например, я могу сделать …
std::cout << typeid(int).name() << std::endl;
…и получить приличное поведение от программы … но это не скомпилируется …
std::type_info a(int);
std::cout << a.name() << std::endl;
Выходы компилятора:
type_info.cpp: In function 'int main()':
type_info.cpp:6:17: error: request for member 'name' in 'a', which is of non-class type 'std::type_info(int)'
…и я не могу сделать …
if(a == typeid(int)) {/*Do something*/ } //Looong error message
Что мне не хватает?
Прежде всего, неприятный анализ:
std::type_info a(int);
a
это функция (принимая int
и возвращаясь std::type_info
).
Во-вторых, std::type_info
не копируется, поэтому вы не можете сохранить его по значению. Вы можете использовать ссылку, если она соответствует вашим потребностям:
const std::type_info &a(typeid(int));
Если вам нужно на самом деле хранить std::type_info
объекты (как будто) «по значению» используют std::type_index
вместо; это было разработано для этого:
std::type_index a(typeid(int));
std::cout << a.name() << std::endl;
std::type_info
не является ни копируемым, ни копируемым. Таким образом, вы не можете делать такие вещи, как std::type_info a = typeid(...)
,
const std::type_info &someTypeId(typeid(someType));
Вы также можете сохранить указатель на std::type_info
объект, потому что typeid возвращает lvalue.
Существует также std::type_index
если вы хотите использовать std::type_info
объекты как ключ в контейнерах. По сути, это тонкая оболочка вокруг указателя на std::type_info
, std::type_index
это особенность C ++ 11