Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Why is Jackson TypeReference abstract?

Tags:

java

jackson

Why is Jackson's TypeReference abstract? It generally makes usages uglier since you need to include braces to create an inline class (and most linters force you into no curly braces on same line).

https://github.com/FasterXML/jackson-core/blob/master/src/main/java/com/fasterxml/jackson/core/type/TypeReference.java

new TypeReference<Map<String, String>>() {
};

Is this due to some obscure Java language limitation?

like image 237
Cheruvian Avatar asked Aug 26 '26 18:08

Cheruvian


1 Answers

JB Nizet has answered why. I just wanted to demonstrate the principle of action.

You can try this for yourself on other classes:

List<String> a = new ArrayList<String>();
List<String> b = new ArrayList<String>() {};

System.out.println(a.getClass().getGenericSuperclass());
System.out.println(b.getClass().getGenericSuperclass());

Ideone demo

Output:

java.util.AbstractList<E> 
java.util.ArrayList<java.lang.String>

As you can see, creating the anonymous subclass preserves the type information about what the concrete generic type of the list is at runtime.

A TypeReference does much the same:

new TypeReference<Map<String, String>>() { }

has a generic superclass:

 TypeReference<java.util.Map<java.lang.String, java.lang.String>>

and from this, you can get the type Map<String, String>. If you created a type reference for another type:

    new TypeReference<Map<Integer, Integer>>() { };

you could get the type Map<Integer, Integer>>, which is separate from Map<String, String>.

If TypeReference were non-abstract, you could write:

TypeReference<Map<String, String>> p = new TypeReference<>();
TypeReference<Map<Integer, Integer>> q = new TypeReference<>();

but the types of p and q would be indistinguishable.

like image 197
Andy Turner Avatar answered Aug 29 '26 08:08

Andy Turner



Donate For Us

If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!