How to get the <?> value for a Foo<?> object? - java

(This is somewhat a followup to my previous question)
I've got a Foo<?> object, foo. Foo<T> is an interface.
How to get the type value hidden behind the <?>?
Note that this is not trivial, as foo can be for example an object of class Bar<String>, where Bar<T> implements Foo<T>, or some anonyomus class implementing interface FloatFoo, where FloatFoo extends Foo<Float>. I need a solution that works in all cases.
Thanks in advance :)

This is not possible using reflection because Java Generics has the problem of Type Erasure. At runtime the types that have been defined for the generic class Foo have been removed, so using reflection on that class will not yield its generic type. This type information is used only in compilation for type safety.
C# does not have this issue and it is possible to access the templatized type of a Class.
This is a overview of the differences.

Well, for short, you can't.
However, what you can do is get the value of <?> when using FloatFoo.
Indeed, from what I remember, generics are not kept in class information.
however, when you create a subtype (be it class or interface) of a generics type, the generics information has to be memorized as it may define some of the subtype's methods signature.
As an example, if your Foo interfaceis declared as it :
public interface Foo<T> {
public T doIt();
}
Having a
public interface FloatFoo extends Foo<Float>
implies this interface has a
public Float doIt();
method declared.
For that, the compiler has to have the type information. And this information will be reflected in the reflection API by the fact that FloatFoo's super class will have some Type parameters associated to it. Or it least it is what I remember from the few cases I encountered such cases (or elaborated them, as it may sometimes be mandatory)
But you'll have far more complete informations at Angelika's generics FAQ.

The final-final (and perhaps the best possible) solution: I refactored my code, so it doesn't need this. I moved all code which needed the type parameter into Foo, so I could provide appropriate implementation within the class. It turned out to be much less code.

I ended up with creating a getType() method in the interface:
Class<T> getType();
Maybe it's not the most elegant solution, but definitely the simplest one.

Related

How can I use a Dynamically created class as Generics?

My problem is I do have a class that is created, compiled and initialized at runtime. I did this as writing the file as TestClass which is File f,
then compile with:
JavaCompiler compiler = ToolProvider.getSystemJavaCompiler();
compiler.run(null,null,null,f.getPath());
After that I load my class and use my methods etc. according to this example;
http://viralpatel.net/blogs/java-dynamic-class-loading-java-reflection-api/
Now my problem is I need to do this:
MyTask<T> m = new MyTask<T>(0,0,0);
T should be my dynamically created class instead of Integer.class etc. However I couldn't find a way for it yet. If you do examine the example at the link I gave above, you will see I can have a instance of my class as in Object form and I can a Class instance for my dynamic class. However, whatever I tried I couldn't find the solution for this.
It keeps saying that Class myClass, can not be used as a type. So how can I use this dynamically created class as a type. Thank you very much.
There is no useful way to express in source code a type that does not exist at compile time. It would not anyway gain you anything more than using Object as a type parameter could do, because Java generics provide compile-time type checking, not run-time type checking.
It might be that your purposes could be served by creating an interface that your dynamic class will implement, and using the interface type as your type parameter.
You can't due to the fact that the generic type information is available only at compile time. When you create a class at runtime, there's no generic information available anywhere any more.
If your class implements an interface, you should use that as the type in code. Something along the lines of
MyInterface foo = myDynamicClass.newInstance();
someGenericMethod(foo);
public <T extends MyInterface> void someGenericMethod(T param) {}
// Or more likely, if there's no other classes that extend MyInterface
public void someGenericMethod(MyInterface param) {}
Of course it may not make any sense to even bother with generic type information, since it's used for static type checking and you're working with a dynamic class.

Keyword extends with Type Parameter<T> in Generic Java

Consider
Gen<T>
So, when I write something like this
Gen<Integer> someRef = new Gen<>();
Gen<String> someRef = new Gen<>();
As per my understanding,
The Java compiler does not actually create different versions of Gen,
or of any other generic class. Although it’s helpful for me to think in these terms,
it is not what actually happens. Instead, the compiler removes all generic
type information, substituting the necessary casts, to make my code behave
as if a specific version of Gen were created.
Thus, there is really only one version of Gen that actually exists in my program.
The process of removing generic type information is called erasure.
Now consider this one,
interface MinMax<T extends Comparable<T>> {
In general, a generic interface is declared in the same way as is a
generic class.
In this case, the type parameter is T, and its upper bound is Comparable, which is an
interface defined by java.lang. A class that implements Comparable defines objects
that can be ordered. Thus, requiring an upper bound of Comparable ensures that MinMax
can be used only with objects that are capable of being compared. Notice that
Comparable is also generic. (It was retrofitted for generics by JDK 5.)
It takes a type parameter that specifies the type of the objects
being compared.
Next, MinMax is implemented by MyClass.
Notice the declaration of MyClass, shown here:
class MyClass<T extends Comparable<T>> implements MinMax<T> {
Here comes my confusion,
When I will write something like this,
MyClass<Integer> ......
Type parameter T will be replaced by Integer. or say any other version(depends on type of Objects I will be operating).
I know very well that a class implements an interface. With regard to aforementioned, wouldn't the above case work like this,
class MyClass<Integer(or some other version) extends Comparable<Integer>> implements MinMax<Integer> {
So, how come a class here is extending an interface,
Integer(or some other version) extends Comparable<Integer>
I know for sure, my understanding is not correct regarding the above context. Kindly elaborate?
The reason is that in Generics the keyword extends is used in a different context.
In Generics, T extends Something denotes that T will be a sub-class of Something or will implement Something (in the cases of an interface). The type of the bound doesn't really matter (class or interface) - what matters is T to be sub-type of the provided bound.
More info:
Why extends interface instead of implements interface?

Get class object from generic type

I want to simplify a project by removing useless classes. By useless classes I mean something like :
public class MainPage extends TileGridFragment<MainModel> {}
The whole logic of this class is implemented by TileGridFragment, and the data is provided by MainModel, which instance is accessed thanks to a singleton class.
I want to defer the instanciation of such class to a later time, so I simply pass MainPage.class to my methods.
As MainPage is equivalent to TileGridFragment<MainModel>, I would like to remove this class and instead use something like TileGridFragment<MainModel>.class instead.
But this doesn't work and I'm out of idead.
I've also tried Class.forName, but its throws a ClassNotFoundException.
Any idea ?
If the implementation of MainPage is actually {}, just pass TileGridFragment.class. The actual type parameters are irrelevant on runtime because they are removed by erasure.
Also, because of erasure, you can cast the new TileGridFragment (with a raw type, as the result of TitleGridFragment.class.newInstance()) to TitleGridFragment<MainModel>, and ther will be no collateral damages (other than a little warning from the compiler, that can be supressed).
You can't really, you might get some joy from reflection but I'm not sure exactly what you're trying to do.
Try here:
Get generic type of class at runtime

Generic class to derive from its generic type parameter

Compiles:
public class SerializableObject<T> implements Serializable
{
public T m_object;
}
Does NOT compile:
public class SerializableObject<T> extends T implements Serializable
{
}
So, I want a generic class to derive from its generic type parameter.
Why?
Let's say I have a Map<K, V> and I simply want to serialize it.
I also don't know ahead which keys I'll have.
How do I do that?
So, I want a generic class to derive from its generic type parameter.
You just can't do that, I'm afraid. There are various technical reasons for this, not least of which is type erasure.
You should look for an alternative solution to your issues - this idea is a dead end.
Nope, your goal is near a Dynamic type, which java does not support.

Can I guarantee typing on an argument's class AND interface?

I am using the GWT library. There is a base class called Widget that all Widgets inherit from. Some Widgets implement certain interfaces (for example HasText), others do not. Sometimes I wish to guarantee that something being passed as an argument to a function is of a certain class AND implements a certain interface.
For example, I wish to have a function that takes a argument X, where X is of the class type Widget AND of the interface type HasText. I wish to have this behavior because only Widgets can be added to Layout containers, and HasText specifies the complete set of behaviors that I actually need from said Widget.
In pseudocode form, it might be:
public void fx(I_AM_A_Widget_AND_IMPLEMENT_INTERFACE_HasText x){
//do stuff with x, which is guaranteed to be a Widget AND implement HasText
}
Is this in any way possible in Java? If there are multiple ways to do so, is there a preferred/better way?
You might be able to use a generic method here:
public <T extends Widget & HasText> void fx(T x)
The compiler will infer the type of T automatically, so no extra syntax when calling the method.
The way I would handle this is to add a method to the HasText interface to return the Widget, and the implementation would just return this.
public class MyClass extends Widget implements HasText {
#Override
public Widget getMyWidget() {
return this;
}
}
So if a method needs a Widget, you just call the HasText's getMyWidget() method. It does create some boilerplate, but it helps with the static type checking.
If you don't care that much for the static type checking, you could simply have a contract (statement in the JavaDoc) that the HasText interface is only intended to be implemented on Widgets, and then just cast whenever you need the Widget.
Then you method just looks like
public void fx(HasText text) //...
Thank you for both of your solutions. In the end, I decided that the best solution was to simply specify bounded types at the top of the class definition. For example, I used the form
public class Example<Editable extends Widget & HasText> {
private Editable editor = null;
//do stuff in various methods (including the constructor) with the
//editor variable and the Editable type.
}
I picked this solution for a few reasons.
The two above mentioned solutions both require the use of methods (boilerplate) that do not really relate to business functionality, but are instead related to circumventing the limitations of the language.
Anon, your solution is correct, but I have the problem of being unable to declare a variable that would hold a reference to the generic object your method returns. I believe this to be the case because the generic object returned from your method only exist at the level of the method, and not the class. Perhaps I have missed some syntax that would allow me to declare variables that have generic properties?
Yishai, your solution works as well, but then I have the problem of having to declare a separate method in every interface that I wish to guarantee support for, this seemed cumbersome.
These bounded types declared in the class "header" only need be declared once. It seems like the most terse declaration of generic bounded types available in Java.
You can declare more than one bounded type in the class "header".
If you use this method exclusively, all the potential bounded types are declared at the same location in your code.
The declaration of bounded types in the class header is the best solution I have run across. I would still be interested in knowing if their is a way to permanently declare (so that it might be accessed across different classes) a bounded type, rather than declaring them per class.

Categories