I'm porting Java7 code to Java8, and I came up with a following problem. In my codebase I have two methods:
public static <T> ImmutableSet<T> append(Set<T> set, T elem) {
return ImmutableSet.<T>builder().addAll(set).add(elem).build();
}
public static <T> ImmutableSet<T> append(Set<T> set, Set<T> elemSet) {
ImmutableSet.Builder<T> newSet = ImmutableSet.builder();
return newSet.addAll(set).addAll(elemSet).build();
Compiler returns error about ambiguous match for method append in following test:
@Test(expected = NullPointerException.class)
public void shouldAppendThrowNullPointerForNullSecondSet() {
ImmutableSet<Integer> obj = null;
CollectionUtils.append(ImmutableSet.of(1), obj);
}
Compiler error:
reference to append is ambiguous both method append(java.util.Set,T) in CollectionUtils and method append(java.util.Set,java.util.Set) in CollectionUtils match
How to rewrite these functions to work with type inference from introduced with Java8?
You've found the new Generalized Target-type Inference improvements in Java 8. There's a few stack overflow questions on it. Such as this one.
Java 8 can infer the return type of a generic based on the method it's passed to as an argument. So when you call CollectionUtils.append(ImmutableSet.of(1), obj)
, Java 8 is attempting to return an immutable set from the static of
call that matches one of your append
methods. In this instance, it could think about returning a ImmutableSet<Object>
instead of the ImmutableSet<Integer>
that you're clearly trying to return. And then it's unclear if you're calling append(Set<Object>, Object)
, or append(Set<Integer>, Set<Integer>)
.
The easiest solution is to rename the second method appendAll
. Or, you could follow the suggested fix here and change your call to something like :
CollectionUtils.append(ImmutableSet.<ImmutableSet<Integer>>of(1), obj);
I'd stick with renaming the second method myself though. It will save other developers the same grief when they try to use the library.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With