What i have done is to just get to know how Generics works in Java. I have written the following code:
public class Test {
public static void main(String... args) throws Exception{
Foo o = new Foo<Integer>(new Integer(5));
o.fun();
}
}
class Foo<T> {
private T t;
public Foo(T t) throws InstantiationException, IllegalAccessException{
System.out.println("1. T is "+t.getClass());
this.t = (T)"test";
System.out.println("2. T is "+t.getClass());
}
void fun(){
System.out.println("3. T is "+t.getClass()+" t = "+t);
}
}
And output is
1. T is class java.lang.Integer
2. T is Still class java.lang.Integer
3. T is class java.lang.String t = test
My question is Why this is changing Class from Integer to String and not showing error/exception.
And second thing is that when I write t = 9;
in function fun()
, it shows:
incompatible types
required: T
found: java.lang.Integer
How do generic classes work and how are they used?
Your response will be greatly appreciated!!
You have declared a generic with no upper bound. Replacement for an unbounded generic
is Object
itself
This means, when the class file gets generated your Foo<T>
class looks something like this
class Foo {
private Object t;
public Foo(Object t) throws InstantiationException, IllegalAccessException{
System.out.println("1. T is "+t.getClass());
this.t = (Object)"test";
System.out.println("2. T is "+t.getClass());
}
void fun(){
System.out.println("3. T is "+t.getClass()+" t = "+t);
}
}
This is due to the fact that, generics are only there to ensure compile time type safety . In run-time they are erased
Considering this
this.t = (Object)"test";
is a valid statement, because Object
is super class of all the classes and this.t
then on becomes a String
The reason for 2. T is Still class java.lang.Integer
,
t
is a parameter to the constructor and the parameter still points to Integer
(not overwritten)this.t