120 likes | 232 Vues
This paper explores the intricate role of wildcards in Java's type system, shedding light on the necessity of use-site variance over traditional covariance. It discusses real-world implications where wildcards enhance type safety and highlights the operational methods for generic programming in Java. The authors delve into type casting, the complexity of subtyping rules, and propose solutions for existing challenges in the type system. Through theoretical insights and practical examples, this research aims to improve developers' understanding and effective usage of wildcards in Java.
E N D
Taming Wildcardsin Java’s Type System Ross Tate Alan Leung Sorin Lerner University of California, San Diego
Why Use Wildcards? Not covariant Need use-site variance Used only once What about List〈Integer〉? long average(List nums) { long sum = 0; for (Object num : nums) sum += ((Number)num).longValue(); return sum / nums.size(); } long average(List〈Number〉 nums) { long sum = 0; for (Number num : nums) sum += num.longValue(); return sum / nums.size(); } 〈P extends Number〉 long average(List〈P〉 nums) { long sum = 0; for (Number num : nums) sum += num.longValue(); return sum / nums.size(); } long average(List〈? extends Number〉 nums) { long sum = 0; for (Number num : nums) sum += num.longValue(); return sum / nums.size(); } Runtime Type Cast
Why Use Wildcards? Inexpressible with polymorphism 〈P〉 void addSuperclasses(Class〈P〉 c, List〈? super Class〈? super P〉〉 list) { Class〈? super P〉 sup = c.getSuperclass(); if (sup != null) { list.add(sup); addSuperclasses(sup, list); } } Untypeable with use-site variance ∃X : X :> P. Class〈X〉
Open Problems with Wildcards Solved • No known subtyping algorithm • Subtyping rules are overly restrictive • Join algorithm is incomplete • Type checker is non-deterministic • Type checker can affect program semantics
Broken Subtyping Algorithm class Numbers〈P extends Number〉 extends ArrayList〈P〉 {} List〈Numbers〈?〉〉<: List〈? extends List〈? extends Number〉〉 No javac Java Yes class C〈P〉 extends D〈D〈? super C〈L〈P〉〉〉〉 {} C〈X〉<: D〈? super C〈X〉〉 No Stack Overflow javac Java
False Negatives class Numbers〈P extends Number〉 extends ArrayList〈P〉 {} List〈? extends List〈? extends Number〉〉 List〈? extends List〈?〉〉 List〈? extends ArrayList〈?〉〉 List〈? extends Numbers〈?〉〉 List〈Numbers〈?〉〉 extends Number direct supertype extends Number direct supertype extends Number direct supertype
Our Algorithm Sound & Complete (if it terminates) class Numbers〈P extends Number〉 extends ArrayList〈P〉 {} List〈Numbers〈?〉〉<: List〈? extends List〈? extends Number〉〉 Numbers〈?〉<: List〈? extends Number〉 Numbers〈X〉<: List〈? extends Number〉 List〈X〉<: List〈? extends Number〉 X <: Number Instantiation X <: Number Context Opening Inheritance Instantiation Assumption
Non-Termination Contrived class C〈P〉 extends D〈D〈? super C〈L〈P〉〉〉〉 {} C〈X〉<: D〈? super C〈X〉〉 D〈D〈? super C〈L〈X〉〉〉〉<: D〈? super C〈X〉〉 C〈X〉<: D〈? super C〈L〈X〉〉〉 D〈D〈? super C〈L〈X〉〉〉〉<: D〈? super C〈L〈X〉〉〉 C〈L〈X〉〉<: D〈? super C〈L〈X〉〉〉 Inheritance Infinite Proof of Subtyping Instantiation Inheritance Instantiation
Restrictions Termination Guaranteed Contrived Inheritance Restriction No use of ? super in the inheritance hierarchy Parameter Restriction When constraining type parameters,? super may only be used at covariant locations class C〈P〉 extends D〈D〈? super C〈L〈P〉〉〉〉 {} Contrived 〈P extends List〈List〈? super C〈L〈P〉〉〉〉〉
Survey No Violations of Our Restrictions 9.2 Million Lines of Code Analyzed Wildcards in Inheritance Wildcards in Constraints 10000 100000 1000 0 Only Unconstrained Wildcards # of Superclass Declarations All at covariant locations
Summary of Contributions • Sound and Complete Subtyping Algorithm • given practical language restrictions • Theory of Existential Types • design of implicit constraints • Techniques for Type-Argument Inference • lazy joins for wildcards • Fixes to the Type System • improved equivalence and intersections • Compatible Extensions to Java • mixing use-site and declaration-site variance