Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Is downcasting (i.e. casting to derived type) ALWAYS wrong? [closed]

Tags:

oop

What is your perspective on downcasting? Is it ALWAYS wrong, or are there cases where it is acceptable, or even preferable or desired?

Is there some good measure/guideline we can give that tells us when downcasting is "evil", and when it's "ok"/"good"?

(I know a similar question exists, but that question spins out from a concrete case. I'd like to have it answered from a general design perspective.)

like image 642
Håvard S Avatar asked Feb 14 '10 20:02

Håvard S


People also ask

Why downcasting is not possible?

Downcasting is not allowed without an explicit type cast. The reason for this restriction is that the is-a relationship is not, in most of the cases, symmetric. A derived class could add new data members, and the class member functions that used these data members wouldn't apply to the base class.

Is downcasting always type safe?

Upcasting is always safe and never fails. Downcasting can risk throwing a ClassCastException, so the instanceof operator is used to check type before casting.

What is the difference between Upcasting and downcasting?

Upcasting (Generalization or Widening) is casting to a parent type in simple words casting individual type to one common type is called upcasting while downcasting (specialization or narrowing) is casting to a child type or casting common type to individual type.

Why downcasting is not used in Java?

Upcasting is allowed in Java, however downcasting gives a compile error. The compile error can be removed by adding a cast but would anyway break at the runtime.


2 Answers

No, it's definitely not always wrong.

For example, suppose in C# you have an event handler - that gets given a sender parameter, representing the originator of the event. Now you might hook up that event handler to several buttons, but you know they're always buttons. It's reasonable to cast sender to Button within that code.

That's just one example - there are plenty of others. Sometimes it's just a way around a slightly awkward API, other times it comes out of not being able to express the type within the normal type system cleanly. For example, you might have a Dictionary<Type, object> appropriate encapsulated, with generic methods to add and retrieve values - where the value of an entry is of the type of the key. A cast is entirely natural here - you can see that it will always work, and it's giving more type safety to the rest of the system.

like image 190
Jon Skeet Avatar answered Sep 18 '22 01:09

Jon Skeet


It's never an ideal solution and should be avoided wherever possible - unless the alternative would be worse. Sometimes, it cannot be avoided, e.g. pre-Generics Java's Standard API library had lots of classes (most prominently the collections) that required downcasting to be useful. And sometimes, changing the design to avoid the downcast would complicate it significantly, so that the downcast is the better solution.

like image 35
Michael Borgwardt Avatar answered Sep 19 '22 01:09

Michael Borgwardt