Home | Contact Us | FAQ | Search & Site Map | Link to Us
Sign In | Join | Other 45 Sites in Network
HomeAnnouncementsWhite Papers
Discussion GroupsFirst AidDatabasesJavaBeansGUIJava 3DVirtual MachineCORBASecurityToolsGeneral
Java DirectoryOpen Source ProjectsSample Book ChaptersUser GroupsWeb Resources
Related Topics
Databases.NETMore Topics ...

Java Forum / General / November 2005

Tip: Looking for answers? Try searching our database.

Generics and subclasses

Thread view: 
EdwardH - 29 Oct 2005 19:40 GMT
I have two classes, Manager and Data. I use them as follows...

Class Manager
{
    private Vector<Data1> dataVector;

    add()
    {
        dataVector.add( new Data1(blabla) );
    }
}

What I want to do is use the same Manager class use several Data-typed
classes, Data1, Data2 and Data3. They all have the same Interface but
work differently.

Unfortunately Manager doesn't want to work with Interfaces
(DataInterface, for example) because of the "new".

Does anyone have any suggestions as to how to make Manager more flexible?

Will I, as I have feared, have to make a subclass (extends) of Manager
to handle each type of Data?

PS: I've tried using generics ...

Class Manager<DataType>
    private Vector<DataType> dataVector;
    ...
    dataVector.add( new DataType(blabla) );

but once again Java doesn't know how to instanciate DataType. Interfaces
don't have constructors, it says.
EdwardH - 29 Oct 2005 22:30 GMT
> Will I, as I have feared, have to make a subclass (extends) of Manager
> to handle each type of Data?

I've solved my problem, as elegantly as it appears to be possible.

Manager handles Data.

Manager1 handles Data1.
Manager2 handles Data2.

The add() method in Manager is overloaded in each of the subManagers.
Not very elegant, forces one to keep track of all the manager subclasses
but it's better than writing the same code over and over again.
Andrew McDonagh - 29 Oct 2005 23:04 GMT
>> Will I, as I have feared, have to make a subclass (extends) of Manager
>> to handle each type of Data?
[quoted text clipped - 9 lines]
> Not very elegant, forces one to keep track of all the manager subclasses
> but it's better than writing the same code over and over again.

The class names 'Manager' and 'Data' even if only used as examples - are
useless and meaningless.

What does Manager manage?  What actual type are the DataXXX?

Post us your real code and we'll give you several ways of doing it
without resorting to copy and paste, Generics, voodoo....

For a starters, just because your code currently has a new statement,
doesn't mean is has too.

e.g.

Class Manager
{
    private Vector<Data1> dataVector;

    add()
    {
        // Instead of
        // dataVector.add( new Data1(blabla) );

        dataVector.add( DataFactory.createData(blabla);
    }
}

The Factory can decide which actual DataXXX to create...

But this example is difficult to show, because Manager and Data are
rubbish names.

real code = real answers.

Andy
Mike - 30 Oct 2005 00:50 GMT
>> Will I, as I have feared, have to make a subclass (extends) of Manager to
>> handle each type of Data?
[quoted text clipped - 9 lines]
> very elegant, forces one to keep track of all the manager subclasses but
> it's better than writing the same code over and over again.

Why don't you just add an argument to the add-method of your Manager class?

Class Manager {
   private Vector<Data> dataVector;
   add(Data data){
       dataVector.add(data);
   }
}

Data is an interface. You create instances of Data1, Data2, Data3 (all
implementing the Data interface) outside the Manager and add them using the
add method.
If you don't want to create the instances outside the Manager you still need
a way to tell the Manager what kind of Data must be created (unless it's ok
to create them randomly), so you need some kind of argument in the
add-method and use it to determine what kind of Data must be created.
Andrew McDonagh - 29 Oct 2005 23:08 GMT
> I ha

snipped...

> but once again Java doesn't know how to instanciate DataType. Interfaces
> don't have constructors, it says.

Thats because Interfaces are classes, and so can't be created - they are
a means of specifying what a given class looks like - nothing else.

They don't have any implementation, so there's no way for Java to know
what to do even if it let you instantiate them.

What languages do you know - we may be able to show how they are similar
to something from those languages....

Failing that, read the Java tutorial, google for Interfaces, as it
appears you have large gaps in your understanding.
andreas kinell - 31 Oct 2005 18:17 GMT
>I have two classes, Manager and Data. I use them as follows...
>
[quoted text clipped - 16 lines]
>
> Does anyone have any suggestions as to how to make Manager more flexible?

I think what you want is this:

Class Manager
{
   private Vector<DataInterface> dataVector;

    add(){
       dataVector.add( new Data1(blabla) );
   }

}

class Data1 implements DataInterface{
}

notice: the dataVector accepts objects of type DataInterface. When you
actually add data, you will create a Data1 object (with "new") but it will
be of type DataInterface as well.

You seem to have overlooked that you can use Interface types like this:

DataInterface myData = new Data1();

HTH,
andreas
Chris Smith - 06 Nov 2005 03:42 GMT
> What I want to do is use the same Manager class use several Data-typed
> classes, Data1, Data2 and Data3. They all have the same Interface but
> work differently.

You can use a general Manager class for this, but you'll need to play
some tricks to instantiate the Data classes.

public class Manager<T extends Data>
{
   private Class<T> dataClass;
   private Vector<T> dataVector;

   public Manager(Class<T> c)
   {
       dataClass = c;
       dataVector = new Vector<T>();
   }

   public void add()
   {
       try
       {
           T data = dataClass.newInstance();
           dataVector.add(data);
       }
       catch (...) { ... } // error handling omitted
   }
}

NOTE A: The Class<T> parameter is admittedly a bit ugly.  It is required
in order to accomodate type erasure.  On the other hand, at least it's
impossible to pass the wrong class as a parameter because of compile-
time checking of the generic type.

NOTE B: This assumes a zero-argument constructor.  Theoretically, it's
possible to do the same thing with arguments to the constructor.  In
practice, that's a bad idea because you have to clearly document a
complex constructor signature that isn't checked until runtime.  If you
think you need that, then instead consider (a) adding a method to Data  
-- Data.setInitialState or something like that, or (b) using an abstract
factory class instead, so you can create the factory class with no
parameters, and then pass parameters to a nice documented and type-
checked method.

Signature

www.designacourse.com
The Easiest Way To Train Anyone... Anywhere.

Chris Smith - Lead Software Developer/Technical Trainer
MindIQ Corporation



Free Magazines

Get these publications absolutely FREE for up to 12 months. There are no hidden fees and no obligation. Simply choose a title, complete the application form and submit it. Read more ...

Oracle MagazineNetwork ComputingComputer WorldBio-IT WorldeWeekInformation WeekInfosecurity
 
Sign In
Join
My Latest Posts
My Monitored Threads
My Blog
My Photo Gallery
My Profile
My Homepage

Start New Thread
Enable EMail Alerts
Rate this Thread



©2009 Advenet LLC   Privacy Policy - Terms of Use
This website includes both content owned or controlled by Advenet as well as content owned or controlled by third parties.