我正在使用《Effective Java》中概述的 Builder 模式的变体,但我对 Java 泛型的行为感到困惑。
考虑下面的类:
public class Result<T extends Resource> {
//final members
final boolean success;
final T resource;
//private constructor
private Result(Builder<T> builder) {
success = builder.success;
resource = builder.resource;
}
//getters
public boolean isSuccess() {
return success;
}
public T getResource() {
return resource;
}
//static factory method to get a builder
public static <T2 extends Resource> Builder<T2> builder(Class<T2> clazz) {
return new Builder<T2>();
}
//nested Builder class
public static class Builder<T extends Resource> {
boolean success;
T resource;
private Builder() { }
public Builder<T> success(boolean success) {
this.success = success;
return this;
}
public Builder<T> resource(T resource) {
this.resource = resource;
return this;
}
public Result<T> build() {
return new Result<T>(this);
}
}
}
当我有一个 Resource 的具体子类时,这似乎很有效:
Result<Device> result = Result.builder(Device.class).build();
但是,当我从另一个定义具有 Resource 通用子类的方法的类中使用它时,它甚至无法编译:
public <T extends Resource> Result<T> createResult(T resource) {
return Result.builder(resource.getClass()).build();
}
编译错误是:
类型不匹配:无法从 Result<capture#1-of 转换?将 Resource> 扩展为 Result<T>
既然 T 和 T2 都扩展了 Resource,为什么它不能弄清楚 Result.Builder.build() 应该返回泛型类型 T 的 Result 呢?
我发现的一种解决方法是放弃 static builder() 方法并使用类似这样的方法:
public <T extends Resource> Result<T> createResult(T resource) { return new Result.Builder<T>().build(); }
似乎应该有一种方法可以使用静态工厂方法和隐藏构造函数来做到这一点......我错过了什么吗?
慕妹3146593
相关分类