【发布时间】:2013-12-18 22:13:18
【问题描述】:
今天我遇到了关于泛型类型推断的奇怪 javac 行为。这是说明这种奇怪行为的示例类:
import java.util.Map;
import java.util.Collections;
import java.util.HashMap;
public class Test {
protected <T> T strange(T t, Map<String, String> map) {
return t;
}
protected void ok(Map<String, String> map) {}
protected <T> T test(T t) {
T res = strange(t , new HashMap<String, String>());
//Doesn't work
//res = strange(t, new <String, String>HashMap());
ok(new <String, String>HashMap());
res = strange(t, Collections.<String, String>emptyMap());
//Doesn't work
//res = strange(t, Collections.EMPTY_MAP);
res = strange(t, (Map<String, String>) Collections.EMPTY_MAP);
ok(Collections.EMPTY_MAP);
return res;
}
}
通知//Doesn't work cmets。如果你取消注释这段代码,你会得到奇怪的编译器错误:
Test.java:18: error: incompatible types
res = strange(t, Collections.EMPTY_MAP);
^
required: T
found: Object
where T is a type-variable:
T extends Object declared in method <T>test(T)
奇怪的是错误抱怨strange 方法的返回类型是 Object 而不是 T,但是当第二个不安全参数被强制转换为正确的类型时,T 被正确推断。
有人可以解释这是否是正确的行为吗?因为它在我看来很奇怪。它可能是编译器错误吗?
为什么这条线有效
T res = strange(t , new HashMap<String, String>());
而这个不是?
T res = strange(t, new <String, String>HashMap());
我已经用 java 7 和 6 对其进行了测试。
【问题讨论】:
-
Java 有语法规则。这个
new HashMap<String, String>());与new <String, String>HashMap());完全不同。 -
有什么区别?
-
哦,我现在明白了。它在您的comment 中进行了描述。但这并不能回答我关于推断 Object 而不是 T 的问题的原始问题
-
这不是唯一的原因。我会尽快写点东西。
标签: java generics type-inference inferred-type