error
public class DefaultLiteProcessScopeFactory<S extends DefaultLiteProcessScope> implements LiteProcessScopeFactory<S> { @Override public S build() { return new DefaultLiteProcessScope(); } }
right
public class DefaultLiteProcessScopeFactory<S extends DefaultLiteProcessScope> implements LiteProcessScopeFactory<S> { @Override public S build() { return (S) new DefaultLiteProcessScope(); } }
DefaultLiteProcessScope extends DefaultLiteProcessScope,but it is till need to be cast?why?
Advertisement
Answer
What you are doing here is wrong. You want to return some subtype of DefaultLiteProcessScope
from the build
method. However, you hard code the return type like this: new DefaultLiteProcessScope()
. Now think of a slightly contrived example like this.
static class SubType extends DefaultLiteProcessScope { }
And a client code that follows.
final LiteProcessScopeFactory<SubType> f = new DefaultLiteProcessScopeFactory<>(); final SubType result = f.build();
Now, since you have hard-coded the return type your compiler can’t vouch for the type safety of the code. I wanted it to return the sub type, however you have hard-coded the super-type instead. So, it asks you to add an explicit cast, which is fair, isn’t it? In fact, this cast fails at runtime throwing a java.lang.ClassCastException
since super type DefaultLiteProcessScope
cannot be cast to the subtype SubType
.
How to fix.
A much better approach would be to pass in a supplier to your build method as an argument like so.
static class DefaultLiteProcessScopeFactory<S extends DefaultLiteProcessScope> implements LiteProcessScopeFactory<S> { @Override public S build(Supplier<S> s) { return s.get(); } } static interface LiteProcessScopeFactory<S> { S build(Supplier<S> s); }
Here’s the new client code.
final LiteProcessScopeFactory<SubType> f = new DefaultLiteProcessScopeFactory<>(); final SubType result = f.build(SubType::new);