Reputation: 121
I recently read that I should use general classes instead of specific classes when proramming. I can't figure out why it is suggested.
example: Let's say that we have a class MyPanel that inherits from JPanel. MyPanel a non-inherited method called getLastChild.
instead of:
MyPanel panel = new MyPanel():
Component last = panel.getLastChild();
it is suggested to do this:
JPanel panel = new MyPanel();
Component last = ((MyPanel)panel).getLastChild();
I don't see why I should choose the second one.
Upvotes: 1
Views: 173
Reputation: 19847
A good example would be:
List<Integer> list = new ArrayList<Integer>;
instead of
ArrayList<Integer> list = new ArrayList<Integer>;
tl;dr It gives you more flexibility and generalizes your code for free.
Whenever you want to pass a list
you will use List
instead of ArrayList
. For example you have a method:
public void doSomething(List<Integer> list)
Later you can change your implementation easily if you realize that for example LinkedList
is a better choice.
Upvotes: 0
Reputation: 115388
You can now develop utility method that operates with JPanel
s. Let's call it foo(JPanel p)
.
Now you can use it with any JPanel
including MyPanel
. But why? You can define the method as following: foo(MyPanel p)
and use it with MyPanel
until you develop second panel that it called OtherPanel
. You cannot send this OtherPanel
to foo()
that operates with MyPanel
only.
However the first (general) version of foo()
can be used for both and for any other class that extends JPanel
and developed by you, by me or by any other programmer.
I hope that this simple example is enough to understand the need of generalization.
Upvotes: -1
Reputation: 312086
You are correct, this example indeed makes no sense.
The general rule of thumb is that you should use the most general class that still has the appropriate functionality. This way, you allow yourself the freedom to change the concrete class you're using and have the rest of the program continue working. For example, consider the JDK's Collections.sort(List)
. The same method call can be used with an ArrayList
, a LinkedList
, or any other List
- it does not care about the specifics of how that list is implemented, just about the fact that it's a list.
Your example, however, is different. If you need to call MyPanel.getLastChild()
, you most certainly care about having a MyPanel
- you can't just use any other JPanel
. Since you already have this dependency, it makes no sense declaring your variable as a JPanel
and downcasting it just to call getLastChild()
.
Upvotes: 4
Reputation: 757
That second one brings greater flexibility. If you declare panel to be of type MyPanel, then it can ONLY be MyPanel (or classes that inherit from MyPanel), whereas if you declare panel as type JPanel, it can be a generic JPanel OR any subclass of JPanel (including MyPanel). This makes your code more portable and easier to edit down the road. Your component might only be a MyPanel now, but what if that changes later?
Upvotes: -1