4.B] Write a note on:
i) Bounded Types
ii) Ambiguity Errors
Answer:
i) Bounded Types in Java Generics
Definition:
In Java generics, bounded types are used to restrict the types that can be passed as type parameters. This allows you to define a range of acceptable types, making the code more flexible while still ensuring type safety.
Types of Bounds:
1] Upper Bounded Wildcards (<? extends T>
):
- Restricts the type parameter to be a subtype of a specific class or interface
T
. - Example:
<? extends Number>
means any class that extendsNumber
, such asInteger
,Double
, etc.
2] Lower Bounded Wildcards (<? super T>
):
- Restricts the type parameter to be a supertype of a specific class or interface
T
. - Example:
<? super Integer>
means any class that is a supertype ofInteger
, such asNumber
orObject
.
3] Unbounded Wildcards (<?>
):
- Allows any type to be passed as a type parameter.
- Example:
<?>
could be any class or interface.
Example of Upper Bounded Type:
class Box<T extends Number> { // T is bounded to be a subclass of Number private T value; public Box(T value) { this.value = value; } public void showType() { System.out.println("Type of T is: " + value.getClass().getName()); } public double getDoubleValue() { return value.doubleValue(); } } public class BoundedTypeExample { public static void main(String[] args) { Box<Integer> intBox = new Box<>(10); intBox.showType(); System.out.println("Double value: " + intBox.getDoubleValue()); Box<Double> doubleBox = new Box<>(99.99); doubleBox.showType(); System.out.println("Double value: " + doubleBox.getDoubleValue()); } }
Explanation:
- Here,
T extends Number
means that the type parameterT
can only be a subclass ofNumber
, likeInteger
,Double
, etc. - This ensures that the
getDoubleValue()
method can be safely called since all subclasses ofNumber
have adoubleValue()
method.
ii) Ambiguity Errors in Java Generics
Definition:
Ambiguity errors in Java generics occur when the compiler cannot determine which method or constructor to invoke due to overlapping generic types or conflicting method signatures. These errors are often caused by type erasure, a process where the generic type information is removed at runtime, leading to potential conflicts.
Common Causes:
Overloading Methods with Generics:
- If you overload methods with the same name but different generic parameters, the compiler might not be able to distinguish between them after type erasure.
Generic Constructors with Conflicting Signatures:
- Similar to methods, constructors with generic parameters can also cause ambiguity if their signatures conflict after type erasure.
Example of Ambiguity Error:
class AmbiguityDemo { // Method 1 public <T> void display(T param) { System.out.println("Generic method: " + param); } // Method 2 (causes ambiguity) public void display(String param) { System.out.println("String method: " + param); } public static void main(String[] args) { AmbiguityDemo obj = new AmbiguityDemo(); obj.display("Hello"); // Ambiguity: Which method should be called? } }
Explanation:
- In the above code, the
display
method is overloaded: one is a generic method, and the other takes aString
parameter. - When
obj.display("Hello")
is called, the compiler is unsure whether to call the generic method (which can accept any type) or theString
method, leading to an ambiguity error.
Resolving Ambiguity:
- To resolve such ambiguity, you can rename the methods to avoid conflicts or use more specific types to make the method signatures distinct.
Summary:
- Bounded Types allow you to restrict the type parameters to a certain range, ensuring that the generic types used are within a specific hierarchy.
- Ambiguity Errors occur when the compiler cannot distinguish between overloaded methods or constructors due to type erasure or conflicting signatures, and they can often be resolved by making method signatures more specific or renaming conflicting methods.