我不完全同意接受的答案,其中说:
在这种情况下,您需要通过显式指示您期望的返回类型来给编译器一点帮助。
这对我来说听起来不对。据我了解泛型方法和类型推断,方括号中提供的类型并不直接指示泛型方法的返回类型。相反,类型T
可以是与泛型方法相关联的返回类型、参数类型、局部变量类型。
T
实际上,由于类型推断机制,我们在大多数情况下(不仅在某些情况下)不需要指定类型参数。在您的示例中,<T>
可以ObjectGenerator.<T> getObject(objectName)
像在大多数其他情况下一样从方法调用中安全地省略 。这是因为T
泛型方法的类型可以很容易地从结果被分配或返回的类型中推断出来。换句话说,由于您private T object
在方法调用之前声明类型T
将被成功推断为T
.
我的主张可以得到权威教程中的以下声明的支持:
类型推断是 Java 编译器查看每个方法调用和相应声明以确定使调用适用的类型参数(或参数)的能力。推理算法确定参数的类型,以及分配或返回结果的类型(如果可用)。最后,推理算法试图找到适用于所有参数的最具体的类型。
关于推理如何工作的两个示例:
static <T> T pick(T a1, T a2) { return a2; }
Serializable s = pick("d", new ArrayList<String>());
该类型T
是Serializable
根据声明的受让人类型推断的。
public static <U> void addBox(U u, java.util.List<Box<U>> boxes) {}
BoxDemo.<Integer>addBox(Integer.valueOf(10), listOfIntegerBoxes);
类型U
是Integer
根据传递参数的类型推断的(即Integer.valueOf(10)
类型为Integer
)。因此,<Integer>
可以从上面的方法调用中安全地省略 。
总而言之,除非我们无法从泛型方法的实参类型或分配或返回结果的类型(调用方法时)推断出泛型方法的类型参数,否则我们可以安全地在方法之前省略类型说明调用。