I have superclass Foo. And a class Bar extending it.
public class Bar extends Foo
Function in Foo:
protected void saveAll(Collection<?> many)
Function in Bar:
public void saveAll(Collection<MyClass> stuff) { super.saveAll(stuff); }
Getting error :
Name clash: The method saveAll(Collection<MyClass>) of type Bar has the same erasure as saveAll(Collection<?>) of type Foo but does not override it.
What am I doing wrong?
Generics were introduced to the Java language to provide tighter type checks at compile time and to support generic programming. To implement generics, the Java compiler applies type erasure to: Replace all type parameters in generic types with their bounds or Object if the type parameters are unbounded.
This answer is not useful. Show activity on this post. At runtime, the parameter types are replaced by Object . So saveAll(Collection<?>) and saveAll(Collection<MyClass>) are transformed to saveAll(Collection) . This is a name clash.
Method Type Erasure. For method-level type erasure, the method's type parameter is not stored but rather converted to its parent type Object if it's unbound or it's first bound class when it's bound.
Generics allow you to create a single method that is customized for the type that invokes it. T is substituted for whatever type you use.
You are overriding the saveAll
method with an incompatible type. Perhaps you want to do something like:
public class Bar extends Foo<MyClass>
Function in Foo<E>
protected void saveAll(Collection<E> many)
and function in Bar:
public void saveAll(Collection<MyClass> stuff) { super.saveAll(stuff); }
Due to the type erasure feature of Java, the JVM will not be able to know whether it is the method that has the parametrized type MyClass or the first one that should be called.
If possible or applicable, the most commonly used pattern I've seen to avoid this is to change the class Foo
to have a parametrized type as well:
public class Foo<T> { protected void saveAll(Collection<T> many) {} }
and then have Bar simply implement Foo
for your specific type:
public class Bar extends Foo<MyClass> { public void saveAll(Collection<MyClass> many) { super.saveAll(many); } }
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