In C++, I want to know whether the actual type of the object is from the same class, not the same class or a derived one. This is similar to the following C# code:
Class Base { } Class Child:Base { } Base childObject = new Child(); If (childObject.GetType() == typeof(Child)) { // do some code } Thanks!
Type checking is the process of verifying and enforcing constraints of types in values. A compiler must check that the source program should follow the syntactic and semantic conventions of the source language and it should also check the type rules of the language.
A type system is a set of rules assigning type expressions to different parts of the program. Type systems can (usually) be implemented in a syntax-directed way. The implementation of a type system is called a type checker.
These terms describe the action of type checking, and both static type checking and dynamic type checking refer to two different type systems.
Every value generated in a program is associated with a type. In a strongly typed language, the language implementation is required to check the types of operands in order to ensure that nonsensical operations, like dividing the integer 5 by the string ``hello'', are not performed.
There are two ways that you can do this. First, you can use the typeid operator, which returns a type_info structure containing information about the type of the object. For example:
Base* ptr = /* ... */ if (typeid(*ptr) == typeid(DerivedType)) { /* ... ptr points to a DerivedType ... */ } Notice that you have to use typeid(*ptr) and not typeid(ptr) here. If you use typeid(ptr), then you'll get back a type_info object for Base*, since the pointer has type Base* regardless of what it points at.
An important point to note is that this will check if what ptr points at is exactly a DerivedType. If ptr is pointing at an object of a type derived from DerivedType (maybe an EvenMoreDerivedType), this code will not work correctly.
An alternative way of checking whether you are pointing at an object of some type that is a bit more robust is to use the dynamic_cast operator. dynamic_cast performs a checked typecast at runtime that will yield a valid pointer if the cast succeeds and nullptr otherwise. For example:
Base* ptr = /* ... */; auto* derived = dynamic_cast<DerivedType*>(ptr); if (derived) { /* ... points to a DerivedType ... */ } This has the added advantage that if ptr points at something like an EvenMoreDerivedType, the cast will still succeed because EvenMoreDerivedType inherits from DerivedType.
As a final thought, you sometimes see code like this:
Base* ptr = /* ... */ if (auto* derived = dynamic_cast<DerivedType*>(ptr)) { /* ... points to a DerivedType ... */ } This locally-scopes the derived pointer to the body of the if statement and uses the fact that nonzero values evaluate to true in C++. I personally find this easier to read and less error-prone, but by all means go with what's easiest for you.
Hope this helps!
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With