Important disclaimer
This is work in progress
Likely to change
I am not an expert
Based on the State of Specialization
document by Brian Goetz (see
resources)
Same things apply to Value Types
The state of generics
Only over reference types
If you want List<int>:
List<Integer> intList = new ArrayList<>();
Performance penalty:
Heade
r
Pointer
Pointer
Pointer
Pointer
Heade
r
int Heade
r
int Heade
r
int Heade
r
int
But why?
Type erasure in generics
public class Box<T> {
private T value;
public Box(T value) {
this.value = value;
}
public T get() {
return value;
}
}
At runtime T is erased to Object
No common “Object” for primitive and
reference types
Why erasure at all?
Use case:
◦ class C uses (or extends) class A
◦ class A is generified
Source and binary compatibility
◦ If class C does not compile: source
incompatibility
◦ If class C should be recompiled to link:
binary incompatibility
No flag day allowed!
Possible approach
Project Valhalla
Compromise #1: current rules for
generics should not be changed
Compromise #2: use separate
approaches for representing different
types
Compromise #3: subclass rules:
ArrayList<int> <: List<int> YES
List<int> <: List<Integer> NO
List<int> <: List<?> NO
List<int> <: List NO
Proposed syntax
Introduce any type variable modifier
public class Box<any T> {
private T value;
public Box(T value) {
this.value = value;
}
public T get() {
return value;
}
}
And then:
Box<int> intBox = new Box<>(42);
What about byte code?
ErasedBox (for reference types)
SpecialBox (for primitive types)
Side note: translations
Heterogeneous translation
◦ Different runtime class for each different
parametric type
◦ Hard to achieve data parametricity (Box<?>)
◦ C++ templates
Homogeneous translation
◦ Same runtime type for all different parametric
types
◦ Java achieved it for reference types
◦ C# for reference and structural types
◦ .NET byte code can range over both types,
Java - not
Representation in bytecode
Erasure of reference types,
specialization for primitives
Look again at SpecialBox usage site:
Class name augmented with
specialization info
Restrictions for any T
Cannot be converted or compared to
null
Cannot be converted to Object or
Object[]
Cannot be used as lock for
synchronization
Cannot convert Foo<any T> to Foo<?>
or Foo
Available only for <any T>
Support for new T[size]
Use it where reference type is allowed
(instanceof)
Foo<any T>.class
Generic methods
Workaround for not allowing raw types
to be passed when <any T> is
expected
Implementation:
◦ A version of the <any T> method should be
specialized
◦ Assumption: methods in a class are fixed
◦ invokedynamic is used
<any T> generic method
public class SpecializedMethod {
public <any T> T returnValue(T value) { return value; }
public static void main(String[] args) {
SpecializedMethod m = new SpecializedMethod();
m.returnValue(42);
}
}
Bytecode at call site:
Migration challenges
Wrong assumptions in some classes:
T[] array = (T[]) new Object();
Problematic overloading
remove(int position);
remove(T element);
Incompletely generified methods
remove(Object)
There’s no null value for primitives
Possible approach: peeling
Implement the backward compatibility method in
reference-specific layer
Add new methods in generic layer
interface List<any T> {
void removeByValue(T element);
void removeByIndex(int pos);
layer<ref T> {
void remove(int pos);
void remove(T element);
default void removeByIndex(int pos) { remove(pos); }
default void removeByValue(T t) { remove(t); }
}
}
The erased class will have all methods
The specialized class will only have generic layer
methods
Time for experiments
ArrayList or Optional class that is generic over
<any T>
Write generic method over <any T> and pass:
reference type, primitive and raw type
Specialized classes as method parameters,
return types of methods in erased generic or
non-generic classes
Usage of static member variables and static
methods of specialized classes
Inner classes combination (specialized in
specialized, specialized in erased, erased in
specialized, specialized in non-generic)
Create new array of T inside specialized generic
class
Call instanceof or .class
Resources
State of Specialization (by Brian Goetz)
http://cr.openjdk.java.net/~briangoetz/va
lhalla/specialization.html
Stewardship the Sobering Parts
https://www.youtube.com/watch?v=2y5
Pv4yN0b0
Source, binary and behavioral
compatibility
https://blogs.oracle.com/darcy/entry/kin
ds_of_compatibility