I have seen one of the old posts on the topic. Due to my new account and lack of reputation points, I cannot comment there; hence, I am making this post.
I was looking in the past for a way to cast shared pointers from one type to another (from base to derived) in order to access some private members on the derived-side. I know its best to avoid downcasting, but this was the framework... Anyway, I saw the answer on the original post was:
std::shared_ptr<A> ap = ...;
dynamic_cast<B&>(*ap).b_function();
if (B* bp = dynamic_cast<B*>(ap.get())
Now, in the command: dynamic_cast<B&>(*ap).b_function()
I understand that the de-referencing symbol here gives us a reference to the pointed object by the shared_ptr . My question is why do we need a reference on the B (i.e. B&)? Couldn't we make it work as:
B& Bref = dynamic_cast<B>(*ap);
Bref.b_function();
I am not very familiar with templates (like shared_ptr is implemented), so I guess its my lack of knowledge on the matter. Could someone please explain to me the meaning behind the & on this context and why the alternative I gave doesn't work?
The point is that a cast to a non-pointer/reference type is always a conversion in C++. You get the converted value which is distinct from the original value. It is a new local object with its own place in memory. Consequently, any change to this copy will not affect the original value at all.
In the case of classes A
and B
, the cast (B)a
would construct the new object by calling the B::B(A&)
constructor of class B
.
Of course, such conversions is not what dynamic_cast<>
is supposed to be used for, so dynamic_cast<>
with a non-pointer/reference type is forbidden by the standard.