Java type erasure

You can work with java generics, but still, don’t understand type erasure? Let’s look at this example:

static <T> String gatherName(T object, Function<T, String> fGetName) {
	return (object == null) ? "" : fGetName.apply(object);
}

The generic T is to perform type check at compile-time. To implement this generic, the compiler will:

  • replace the T parameter with the bound classes or Object
  • insert type casts to preserve type safety
  • generate bridge methods 

A simple use case: print the name of three different instances. 

public static void main(String[] args) {
	Person person = new Person("Alice");
	School school = new School("University of Bologna");
	// bounded to types
	String s1 = gatherName(person, Person::getName);
	String s2 = gatherName(school, School::getSchoolName);
	// unbound, uses an Object
	String s3 = gatherName("a few words", Object::toString);
	System.out.printf(" s1: %s%n s2: %s%n s3: %s%n ", s1, s2, s3);
}

The compiler will see three calls to the generic function name : 

  • <Person> : name( Person o, Function<Person,String> f)
  • <School> : name(School o, Function<Person, String> f)
  • unbound : name( Object o, Function<Object, String> f)

Assuming there are no other calls, it will generate just the three methods above, and for the bound methods it’ll generate proper casts and type bridges.

The generated code (bytecode) does not contain the Type information anymore. If you decompile it to java, you will see there are only three methods and no mention of a generic type. Hence, the generic type was erased.

Categories: Java

0 Comments

Leave a Reply

Avatar placeholder

Your email address will not be published. Required fields are marked *