Does dynamic_cast work even when there is no inheritance? [duplicate] - c++

This question already has answers here:
what is side-cast or cross-cast in Dynamic_cast in C++
(2 answers)
Closed 2 years ago.
std::bad_cast: https://en.cppreference.com/w/cpp/types/bad_cast
An exception of this type is thrown when a dynamic_cast to a reference type fails the run-time check (e.g. because the types are not related by inheritance)
So, if the types are not related by inheritance then it throws an error, so how it the following quote hold true?
https://stackoverflow.com/a/332086/462608
You can use it for more than just casting downwards – you can cast sideways or even up another chain.
What does this quote mean? Please give examples.

Sideways cast would be for example like this:
class Base1 { virtual ~Base1() = default; };
class Base2 { virtual ~Base2() = default; };
class Derived: public Base1, public Base2 {};
int main() {
Base1* p1 = new Derived;
Base2* p2 = dynamic_cast<Base2*>(p1);
}
Types Base1 and Base2 are unrelated to each other, but you can cast between the pointers because Derived inherits from both.
I'm not sure what did the original answerer mean by "cast [...] up another chain", but I guess they meant a situation where you would have a Base1* pointer and would cast to Base2 parent.

Related

How delete knows, where the object starts in the memory? [duplicate]

This question already has answers here:
Is the whole object freed with a non-virtual destructor and a Base class pointer?
(6 answers)
Closed 3 years ago.
Consider following code:
class Base1 { public: int a1; };
class Base2 { public: int a2; };
class Foo: public Base1, public Base2 {}
int main() {
Foo *foo = new Foo();
Base2 *b = foo;
delete b; // note pointer foo != pointer b
}
How delete knows, where the memory, which should be freed, begins?
Since all the classes contain only atomic integers, is virtual destructor needed in this particular case?
is virtual destructor needed in this particular case?
Yes. Deleting an object through a pointer to a base with non-virtual destructor has undefined behaviour.
How delete knows, where the object starts in the memory?
In case of non-virtual destructor, you pass the starting address to the operator (or if you don't, then you have UB), so there's no mystery.
In case of virtual destructor, virtual dispatch is used. The compiler will somehow implement it to work correctly. Typically, a "vptr" is used.

Decay to base class [duplicate]

This question already has answers here:
Get base class for a type in class hierarchy
(4 answers)
Closed 3 years ago.
Is there a trait that returns the base class of a specific class, with the assumption that there is no multiple inheritance involved? Basically something like:
struct Base
{
};
struct Derived : public Base
{
};
struct DerivedDerived : public Derived
{
};
static_assert(std::is_same_v<base<DerivedDerived>::type,Derived>);
static_assert(std::is_same_v<base<Derived>::type,Base>);
static_assert(std::is_same_v<base<Base>::type,Base>);
// with levels
static_assert(std::is_same_v<base<0,DerivedDerived>::type,Base>);
static_assert(std::is_same_v<base<1,DerivedDerived>::type,Derived>);
static_assert(std::is_same_v<base<2,DerivedDerived>::type,DerivedDerived>);
static_assert(std::is_same_v<base<0,Derived>::type,Base>);
static_assert(std::is_same_v<base<1,Derived>::type,Derived>);
Nope. You can test whether a given type inherits from a given other type with std::is_base_of, but not ask for the base type outright. That is, until C++ gets static reflection sometime in the future.

C++ dynamic_cast returning NULL although object is of a derived type [closed]

Closed. This question needs debugging details. It is not currently accepting answers.
Edit the question to include desired behavior, a specific problem or error, and the shortest code necessary to reproduce the problem. This will help others answer the question.
Closed 5 years ago.
Improve this question
I have a strange problem, where a dynamic_cast is returning a NULL pointer although the object given in the expression is of a derived type with an inheritance path to the type of the cast.
Unfortunately, i cannot post original code, so here is the situation roughly reconstructed:
I have a clas hierarchy of the following type:
class A
class B
class C : public A, B
class D : public C
All classes have virtual members.
Now assume I have an object of concrete type D.
In a function where this object is passed in as a B*, i have a cast of this type:
C* func(B* pObject)
{
return dynamic_cast<C*>(pObject);
}
The cast returns NULL although the object seems well defined.
VC++ reports it as being a D when looking at the object in debugger when hovering over pObject. (might this be misleading?)
Is this cast supposed to work?
Imo this cast should be allowed. Am i missing something?
What can i do to analyse this issue?
Could there be an issue with the multiple inheritance?
This is on Visual C++ 2013 Pro if it makes any difference.
Your problem is elsewhere.
Consider
#include <iostream>
struct A {};
struct B {virtual ~B() = default;};
struct C : A, B {};
struct D : C {};
int main()
{
D d;
D* pd = &d;
B* pb = dynamic_cast<B*>(pd);
C* pc = dynamic_cast<C*>(pb);
std::cout << pc; // this is not nullptr
}
This proves that C* is reachable from B* for an pointer to an object of type D, when only B (the source type in the second cast) is explicitly polymorphic.
See https://ideone.com/ifxYgV

Can we perform deleting object through a pointer to one of its base classes? [duplicate]

This question already has answers here:
Does delete work with pointers to base class?
(2 answers)
Closed 7 years ago.
Does it cause UB if we define a virtual destructor? For intance:
struct A{ virtual ~A(){ } };
struct B : A { };
A *a = new B;
int main()
{
delete a; //UB?
}
coliru
It is fine precisely because the destructor is virtual — otherwise it would have been UB.
In other words, if you want to delete objects of derived type, through pointers of base type, then the destructor of base class must be virtual, else it would be UB. That ensures that the correct destructor (i.e the destructor of derived) is invoked — that is called runtime polymorphism.
"Does it cause UB if we define a virtual destructor?"
No that's just fine as the destructor was declared virtual. Stepping up the vtable and calling ~B first will be handled by delete.
Its fine, so long as the destructor is virtual.
If the destuctor is not, it will not know to delete the members of the subclass.

what exactly is dynamic casting in c++ [duplicate]

This question already has answers here:
Regular cast vs. static_cast vs. dynamic_cast [duplicate]
(8 answers)
Closed 9 years ago.
can anyone tell what exactly is dynamic casting means in c++.
where exactly can we use this dynamic casting?
this was asked to me in the interview and i went blank for this question:).
dynamic_cast is casting method to find out the object's class at runtime.
class Base
{
public:
virtual bool func1();
};
class Derived1 : Base
{
public:
virtual bool func1();
virtual bool funcDer1();
};
class Derived2 : Base
{
public:
virtual bool func1();
virtual bool funcDer2();
};
Base* pDer1 = new Derived1;
Base* pDer2 = new Derived2;
Derived2* pDerCasted = dynamic_cast<Derived2*>(pDer2);
if(pDerCasted)
{
pDerCasted->funcDer2();
}
-> We cannot call funcDer2 with pDer2 as it points to Base class
-> dynamic_cast converts the object to Derived2 footprint
-> in case it fails to do so, it returns NULL .( throws bad_cast in case of reference)
Note: Usually, Dynamic_cast should be avoided with careful OO design.
Try to use the search first
old answer
Dynamic casting is safely discovering the type of an object instance at runtime.
This is achieved by the compiler generating reference tables, which can be potentially rather large. For this reason, it is often disabled during compilation if the programmer knows that they do not use the feature.