我正在尝试创建一个 Variable
可以表示 Integer
的类或Double
使用泛型的值。
下面是我尝试过的代码。由于删除,我使用 enum
存储 Variable
的预期类型然后尝试使用它来将值初始化为正确的类型。
public class Variable<T> {
private enum Type {INTEGER, DOUBLE};
private Type type;
private T value;
public static Variable<Integer> createAsInteger() {
return new Variable<Integer>(Type.INTEGER);
}
public static Variable<Double> createAsDouble() {
return new Variable<Double>(Type.DOUBLE);
}
private Variable(Type type) {
this.type = type;
if(type == Type.INTEGER) {
value = new Integer(0);
} else {
value = new Double(0.0);
}
}
public static void main(String[] args) {
Variable.createAsInteger();
Variable.createAsDouble();
}
}
但是,当我编译它时,我收到以下消息...
error: incompatible types: Integer cannot be converted to T
value = new Integer(0);
Double
同样如此.
任何人都可以解释为什么会发生这种情况,以及是否有一种方法可以解决这个问题,而无需编写两个单独的类,一个用于 Integer
和一个 Double
?
编辑
感谢您的所有回答...基于它们,我现在意识到有更好的方法可以做到这一点。不过,我正在努力弄清楚为什么这种方法不起作用,以便我将来不会犯同样的错误。
当我将我的类(class)定义为public class Variable<T extends Number>
时按照建议,我仍然遇到相同的错误。
最佳答案
您的架构似乎玷污了泛型的概念。
最简单的方法是在类型参数中设置上限:
class Variable<T extends Number> {...}
然后你可以使用通用工厂方法创建 Variable<X>
根据您所需的类(class):
static <X extends Number>Variable<X> create() {
return new Variable<X>();
}
然后您可以将其调用为:
Variable.<Integer>create(); // returns an instance of `Variable<Integer>`
这不限于Integer
和Double
,而是任何 Number
。
如果需要,您可以通过执行以下操作来限制这些选择:
- 将参数添加到您的
create
方法:create(Class<X> clazz)
检查您的
clazz
的值方法体内的参数:if (!clazz.equals(Integer.class) && !clazz.equals(Double.class)) { // TODO complain }
否则,您可以确保使用 private
构造函数并提供 static createAs...
非通用方法,例如 createAsInteger
等等,这将返回 new Variable<Integer>
等等
关于具有静态工厂方法的 Java 泛型,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/38847628/