Is there a syntax or workaround to constrain a generic type parameter to any of a range of types?
I am aware that you can constrain a type to be all
Using of instanceof
is considered as not very good style of programming, and allowing you to use OR
in generics implies you will use one.
No. It wouldn't make any sense unless all the types had a non-empty union type, e.g. an interface they all implemented, or a base class they all extended, in which case you just specify the union type.
public class MyWrapper<T extends A | B> {}
You can't do this for interfaces that you don't have control over, but for your own stuff you could use an empty marker interface:
interface AOrB {
}
interface A extends AOrB {
someMethodHere();
}
interface B extends AOrB {
someOtherMethodHere();
}
public class MyClass<T extends AOrB> {}
Regardless of what purists say, using instanceof
is perfectly fine when you need it.
The following code would do the same thing as in the provided example, but without runtime type checking and typecasts.
public boolean sameAs(MyClass obj) {
return this.id.equals(obj.id);
}
public boolean sameAs(String obj) {
return this.id.equals(obj);
}
NPE checking might be a good idea.
While Java has limited support for "intersection types" like T1 & T2
, support for "union types" is scanty.
Generic types with wildcard are actually union types: G<? extends X>
is the union of all G<S>
where S
is a subtype of X
.
No support for union of arbitrary two types.
Java 7's multi-catch syntax looks like it supports union of arbitrary exception types
catch (IOException|SQLException ex){ .. }
but not really, the type of ex
is a fixed super class, not a union of the two classes.