Thanks a lot. Nico. 2007/9/28, Engelking, Nicholas <[EMAIL PROTECTED]>: > Unfortunately, the short answer is that you can't. > > The compiler will yell at you about class literals for generics because in > Java they are implemented using erasure. This is in contrast to C# (which is > where I first learned how to use generics) and annoys many people to no end. > It was done to maintain binary compatibility between generic and non generic > versions of classes and to ensure generic classes could run on JVMs that have > no concepts of generics. The compiler basically makes all your generic > methods use Object and inserts casts that are garneted to be safe by the > compiler. > > At run time the method > Optional opt = composite.<Optional> getFeature(); > Looks like > Optional opt = (Optional) composite. getFeature(); > To the JVM (more or less) > > T.class doesn't work because class literals are resolved at runtime (even > though as a programmer you know what they are at compile time). Since a T > type is really an Object type, T.class makes no sense and doesn't give you > the object you want. > > For the method you describe, you can still avoid the casts using generics but > you need a parameter that takes an object representing a type, not a > parameter that IS a type, since type parameters aren't really method > parameters in the normal sense. > > public <T> T getFeature(Class<T> clazz) { > return aggregators.get( clazz ); > } > > Then you can call the method like so > > Optional opt = composite.getFeature( Optional.class ); > > And there are no casts required. > > This comes from the fact that class objects are now parameratized to there > class. So for example: > > String.class > > Will return a Class<String> object. > > It doesn't seem ideal but it's as close as you can get with the way Generics > are implemented in Java. You will have problems though if the caller of your > method uses type parameters instead of explicit types. For example: > > public class OptionWrapper<T> { > > private final Composite composite; > > public OptionWrapper(Composite composite) { > this.composite = composite; > } > > public T getOpt() { > //needs a class object! > T opt = composite. getFeature(); > return opt; > } > } > > Hope this helps. > -----Original Message----- > From: nicolas de loof [mailto:[EMAIL PROTECTED] > Sent: September 28, 2007 4:54 AM > To: Struts Users Mailing List > Subject: Re: [ot] help on generics... > > Thanks a lot for those detailed examples ! > > I don't want to setup a factory, but to expose internals as optional features > : > > my class is a composite, with a map of "features", where the key is > the feature interface ( > Map<Class, Object>) > > I'd like to get an optional feature using : > > Optional opt = composite.getFeature( Optional.class ); > > The generics way seems to be : > > Optional opt = composite.<Optional> getFeature(); > > How can I then get the Class object used as generics type, to get it > from the map ? > > public <T> T getFeature() > { > return aggregators.get( T.class ); // Doesn't work > } > > > > 2007/9/27, Engelking, Nicholas <[EMAIL PROTECTED]>: > > > > Specifically, you could use > > > > public <T> T getInstance(Class<T> clazz) > > throws InstantiationException, > > IllegalAccessException{ > > return clazz.newInstance(); > > } > > > > The Class<T> object has a method newInstance() that creates an instance of > > a class with the default constructor. The exceptions it throws represent > > cases where you don't have visibility permissions for the constructor, > > there is no default constructor, the class is abstract, or the constructor > > call throws an error (which is then wrapped and rethrown). The method > > outlined above is just a wrapper - if you already have the class object you > > can just instantiate it. If you need to not use the default constructor, > > try something like: > > > > public <T> T getInstance(Class<T> clazz) > > throws IllegalArgumentException, > > SecurityException, > > InstantiationException, > > IllegalAccessException, > > InvocationTargetException, > > NoSuchMethodException { > > return clazz > > .getConstructor( > > Parameter1Type.class, > > Parameter2Type.class) > > .newInstance( > > parameter1, > > parameter2); > > } > > > > The getConstructor methods takes all they types for it's parameters in > > declaration order. This is to resolve the method signature. In this class > > your class would have a constructor: > > > > MyClass(Parameter1Type parameter1, Parameter2Type parameter2){ > > // constructor stuff here > > } > > > > The newInstance method takes the actual parameters to pass to the > > constructor. In this example, they are parameter1 (which is a > > Parameter1Type) and parameter2 (which is a Parameter2Type). The errors > > occur if the constructor doesn't exist, the arguments are the wrong type, > > the caller doesn't have visibility permissions, the class is abstract, or > > the constructor throws an error (which is then wrapped and rethrown). > > > > You could also pass the parameters into the getInstance method and pick out > > the constructer dynamically like so: > > > > public <T> T getInstance(Class<T> clazz, Object... args) > > throws InvocationTargetException { > > T newObject = null; > > for (java.lang.reflect.Constructor<T> c : > > clazz.getConstructors()) { > > // try creating objects with the passed > > // args until one works. > > try { > > newObject = c.newInstance(args); > > break; > > } catch (IllegalArgumentException e) { > > } catch (InstantiationException e) { > > } catch (IllegalAccessException e) { > > } > > } > > return newObject; > > } > > > > This method returns an instance of the class passed created with the > > constructor parameters passed. If the constructor throws an error it is > > wrapped in an InvocationTargetException and rethrown. If no constructor > > matches the method returns null. > > > > > > -----Original Message----- > > From: Giovanni Azua [mailto:[EMAIL PROTECTED] > > Sent: September 27, 2007 11:56 AM > > To: Struts Users Mailing List > > Subject: Re: [ot] help on generics... > > > > how about: > > > > public static <T> T > > getInstance(Class<T> aClass) > > { > > // TODO: > > } > > > > regards, > > Giovanni > > > > nicolas de loof wrote: > > > Hello, > > > > > > my question is fully off topic, but Struts2 is the only java5 project I > > > know. > > > > > > I'd like a method to return an instance of a class passed as parameter : > > > > > > public Object getInstance( Class clazz ) > > > > > > I'd like to use generics to make the return type in sync with the > > > class type. Is this possible ??? > > > > > > --------------------------------------------------------------------- > > > To unsubscribe, e-mail: [EMAIL PROTECTED] > > > For additional commands, e-mail: [EMAIL PROTECTED] > > > > > > > --------------------------------------------------------------------- > > To unsubscribe, e-mail: [EMAIL PROTECTED] > > For additional commands, e-mail: [EMAIL PROTECTED] > > > > > > ******************** > > NOTICE OF CONFIDENTIALITY > > This communication including any information transmitted with it is > > intended only for the use of the addressees and is confidential. > > If you are not an intended recipient or responsible for delivering > > the message to an intended recipient, any review, disclosure, > > conversion to hard copy, dissemination, reproduction or other use > > of any part of this communication is strictly prohibited, as is the > > taking or omitting of any action in reliance upon this communication. > > If you receive this communication in error or without authorization > > please notify us immediately by return e-mail or otherwise and > > permanently delete the entire communication from any computer, > > disk drive, or other storage medium. > > > > If the above disclaimer is not properly readable, it can be found at > > www.td.com/legal > > > > AVERTISSEMENT DE CONFIDENTIALITE > > Ce courriel, ainsi que tout renseignement ci-inclus, destiné uniquement > > aux destinataires susmentionnés, est confidentiel. Si vous > > n'êtes pas le destinataire prévu ou un agent responsable de la > > livraison de ce courriel, tout examen, divulgation, copie, impression, > > reproduction, distribution, ou autre utilisation d'une partie de ce > > courriel est strictement interdit de même que toute intervention ou > > abstraction à cet égard. Si vous avez reçu ce message par erreur ou > > sans autorisation, veuillez en aviser immédiatement l'expéditeur par > > retour de courriel ou par un autre moyen et supprimer immédiatement > > cette communication entière de tout système électronique. > > > > Si l'avis de non-responsabilité ci-dessus n'est pas lisible, vous > > pouvez le consulter à www.td.com/francais/legale > > > > --------------------------------------------------------------------- > To unsubscribe, e-mail: [EMAIL PROTECTED] > For additional commands, e-mail: [EMAIL PROTECTED] > > --------------------------------------------------------------------- > To unsubscribe, e-mail: [EMAIL PROTECTED] > For additional commands, e-mail: [EMAIL PROTECTED] > >
--------------------------------------------------------------------- To unsubscribe, e-mail: [EMAIL PROTECTED] For additional commands, e-mail: [EMAIL PROTECTED]