假设我有两种方法:
public Set<String> method1()
public List<String> method2()
Run Code Online (Sandbox Code Playgroud)
我如何制作一个通用方法?具体来说,我希望通用化“Set”和“List”。
这是一个无效的尝试:
public static <T extends Collection> T<String> genericMethod
Run Code Online (Sandbox Code Playgroud)
它显示了一个编译器错误:类型“T”没有类型参数。
就签名而言,这将是
public static <T extends Collection<String>> T genericMethod() {
...
}
Run Code Online (Sandbox Code Playgroud)
据推测,genericMethod
将T
在某个时候创建一个实例并返回它,而不是仅仅返回null
(这不会很有用,是吗?),但是根本不能保证T
有任何构造函数。由于类型擦除,运行时无论如何都不知道要创建什么类型。为了解决这个问题,该方法还需要接受一个参数,告诉它如何创建一个T
:
public static <T extends Collection<String>> T genericMethod(Supplier<? extends T> tSupplier) {
...
}
Run Code Online (Sandbox Code Playgroud)
现在,与其说new T()
,哪个无效,不如说tSupplier.get()
得到一个T
.
Set<String>
例如,如果调用者想要一个,他们会这样做:
Set<String> set = genericMethod(HashSet::new);
Run Code Online (Sandbox Code Playgroud)
请注意,集合的具体实现现在由调用者指定,而不是作为 的实现细节隐藏genericMethod
。这是不可避免的,因为T
现在不知道集合 ( )的特定类型genericMethod
。