Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Why do generic types have the same signature?

Tags:

java

generics

I have the following generic class:

class Or<A,B>
{
  Or (A a) {}
  Or (B b) {}
}

Why do I get the following error when I try to compile it:

Or(A) is already defined in Or
    Or (B b)
    ^

It seems to me that the two constructors share the same signature although they have different generic type arguments. Why? And how to work around this problem?

Update

I understood the problem now. The compiler needs a way to distinguish the two types. Adding such a constrain would be ok for my use case. So I would like to add another question:

How to specify that the two types A and B may be anything but different?

like image 246
ceving Avatar asked Jul 03 '13 10:07

ceving


3 Answers

It seems to me that the two constructors share the same signature although they have different generic type arguments.

They do. The signature is

Or(Object o);

Why?

Because of type erasure implementation of generics in Java: references to generic types are converted to System.Object in all contexts where they are used; the generic type is known only to the compiler.

And how to work around this problem?

Unfortunately, you cannot easily work around this problem in a constructor. You can replace the overloaded constructors with factory methods, and give different names, say OrWithA and OrWithB:

// Hide the constructor
private Or(...) {
    ...
}
// Publish factory methods
public static <X> Or OrWithA(X a) {
    return new Or(...);
}
public static <X> Or OrWithB(X a) {
    return new Or(...);
}
like image 193
Sergey Kalinichenko Avatar answered Oct 30 '22 05:10

Sergey Kalinichenko


This is because A or B can be anything, they can be same also as generics is just for compile time. At runtime, they are lost due to type erasure

like image 31
Prasad Kharkar Avatar answered Oct 30 '22 05:10

Prasad Kharkar


They just do. That's the nature of generics; they provide syntatic sugar used only at compile time. There is no way round it.

(Acknowledge question comments) This is called type erasure: see http://en.wikipedia.org/wiki/Type_erasure

like image 38
Bathsheba Avatar answered Oct 30 '22 05:10

Bathsheba