'why is this still need to cast in java?
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?
Solution 1:[1]
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);
Solution 2:[2]
The reason is that the code is wrong.
public class MyOtherFactory<SubclassOfDefaultLiteProcessScope> {}
will break because DefaultLiteProcessScope is not a SubclassOfDefaultLiteProcessScope.
Solution 3:[3]
Your code would throw a ClassCastException in the following instance:
class CustomLiteProcessScope extends DefaultLiteProcessScope { ... }
final DefaultLiteProcessScopeFactory<CustomLiteProcessScope> factory = new ...;
And then:
factory.build(); <-- Exception trying to cast DefaultLiteProcessScope to CustomLiteProcessScope
Solution 4:[4]
S extends DefaultLiteProcessScope, so you're trying to return the parent class instance instead of child class instance.
Sources
This article follows the attribution requirements of Stack Overflow and is licensed under CC BY-SA 3.0.
Source: Stack Overflow
| Solution | Source |
|---|---|
| Solution 1 | |
| Solution 2 | kutschkem |
| Solution 3 | PPartisan |
| Solution 4 | Sergej Christoforov |
