Pergunta

Estou me perguntando qual é a diferença entre typeid e typeof em C++.Aqui está o que eu sei:

Além disso, aqui está o teste de código de teste que criei e descobri que typeid não retorna o que eu esperava.Por que?

principal.cpp

#include <iostream>  
#include <typeinfo>  //for 'typeid' to work  

class Person {  
    public:
    // ... Person members ...  
    virtual ~Person() {}  
};  

class Employee : public Person {  
    // ... Employee members ...  
};  

int main () {  
    Person person;  
    Employee employee;  
    Person *ptr = &employee;  
    int t = 3;  

    std::cout << typeid(t).name() << std::endl;  
    std::cout << typeid(person).name() << std::endl;   // Person (statically known at compile-time)  
    std::cout << typeid(employee).name() << std::endl; // Employee (statically known at compile-time)  
    std::cout << typeid(ptr).name() << std::endl;      // Person * (statically known at compile-time)  
    std::cout << typeid(*ptr).name() << std::endl;     // Employee (looked up dynamically at run-time  
                                                       // because it is the dereference of a pointer
                                                       // to a polymorphic class)  
 }  

saída:

bash-3.2$ g++ -Wall main.cpp -o main  
bash-3.2$ ./main   
i  
6Person  
8Employee  
P6Person  
8Employee
Foi útil?

Solução

A linguagem C ++ não tem coisas como typeof. Você deve estar olhando para alguma extensão específica do compilador. Se você está falando sobre o GCC's typeof, então um recurso semelhante está presente no C ++ 11 através da palavra -chave decltype. Novamente, C ++ não tem tal typeof palavra -chave.

typeid é um operador de idioma C ++ que retorna informações de identificação de tipo no tempo de execução. Basicamente retorna um type_info objeto, que é comparável à igualdade com outro type_info objetos.

Observe que a única propriedade definida do retorno type_info Objeto tem é ser igual à igualdade e não igualdade de igualdade, ou seja, type_info objetos que descrevem diferentes tipos devem comparar não iguais, enquanto type_info Objetos que descrevem o mesmo tipo precisam comparar iguais. Todo o resto é definido por implementação. Os métodos que retornam vários "nomes" não têm garantia de devolver qualquer coisa legível por humanos, e mesmo não garantida para devolver nada.

Observe também que o acima provavelmente implica (embora o padrão não pareça mencioná -lo explicitamente) que aplicações consecutivas de typeid para o mesmo tipo pode retornar diferente type_info Objetos (que, é claro, ainda precisam comparar iguais).

Outras dicas

A principal diferença entre os dois é a seguinte

  • Typeof é um tempo de compilação construto e retorna o tipo conforme definido no horário de compilação
  • O TypeId é uma construção de tempo de execução e, portanto, fornece informações sobre o tipo de tempo de execução do valor.

Tipo de referência: http://www.delorie.com/gnu/docs/gcc/gcc_36.html

Referência do TypeID: https://en.wikipedia.org/wiki/typeid

typeid pode operar em tempo de execução e retornar um objeto que descreve o tipo de tempo de execução do objeto, que deve ser um ponteiro para um objeto de uma classe com métodos virtuais para que RTTI (informações de tipo de tempo de execução) para ser armazenado na classe.Ele também pode fornecer o tipo de tempo de compilação de uma expressão ou um nome de tipo, se não for fornecido um ponteiro para uma classe com informações de tipo de tempo de execução.

typeof é uma extensão GNU e fornece o tipo de qualquer expressão em tempo de compilação.Isto pode ser útil, por exemplo, na declaração de variáveis ​​temporárias em macros que podem ser usadas em vários tipos.Em C++, você normalmente usaria modelos em vez de.

Respondendo à pergunta adicional:

Meu código de teste a seguir para o TypeID não produz o nome do tipo correto. o que há de errado?

Não há nada de errado. O que você vê é a representação da string do nome do tipo. O C ++ padrão não força os compiladores a emitir o nome exato da classe, ele cabe ao implementador (fornecedor do compilador) para decidir o que é adequado. Em suma, os nomes estão de acordo com o compilador.


Estas são duas ferramentas diferentes. typeof Retorna o tipo de expressão, mas não é padrão. Em C ++ 0x, há algo chamado decltype que faz o mesmo trabalho Afaik.

decltype(0xdeedbeef) number = 0; // number is of type int!
decltype(someArray[0]) element = someArray[0];

Enquanto typeid é usado com tipos polimórficos. Por exemplo, digamos que cat deriva animal:

animal* a = new cat; // animal has to have at least one virtual function
...
if( typeid(*a) == typeid(cat) )
{
    // the object is of type cat! but the pointer is base pointer.
}

O TypeId fornece o tipo de dados em tempo de execução, quando solicitado. O typedef é uma construção de tempo de compilação que define um novo tipo, conforme declarado depois disso. Não há tipo de saída em C ++ aparece como (mostrado como comentários inscritos):

std::cout << typeid(t).name() << std::endl;  // i
std::cout << typeid(person).name() << std::endl;   // 6Person
std::cout << typeid(employee).name() << std::endl; // 8Employee
std::cout << typeid(ptr).name() << std::endl;      // P6Person
std::cout << typeid(*ptr).name() << std::endl;     //8Employee

Você pode usar o Boost Demangle para realizar um nome bonito:

#include <boost/units/detail/utility.hpp>

E algo como

To_main_msg_evt ev("Failed to initialize cards in " + boost::units::detail::demangle(typeid(*_IO_card.get()).name()) + ".\n", true, this);
Licenciado em: CC-BY-SA com atribuição
Não afiliado a StackOverflow
scroll top