以下内容在jls https://docs.oracle.com/javase/specs/jls/se7/html/jls-18.html
的第18章中定义NonWildcardTypeArguments:
< TypeList >
TypeList:
ReferenceType { , ReferenceType }
ReferenceType:
Identifier [TypeArguments] { . Identifier [TypeArguments] }
TypeArguments:
< TypeArgument { , TypeArgument } >
TypeArgument:
ReferenceType
? [ (extends | super) ReferenceType ]
根据NonWildcardTypeArguments的名称,它不应该允许通配符。但是下面的代码编译
public class NonWildcardTypeArgumentsTest {
public void test(Test<java.util.Set<? extends Object>> args) {
}
}
class Test<T> {}
此示例中的类型参数满足NonWildcardTypeArguments的定义,并且它包含通配符:
<java.util.Set<? extends Object>>
我很困惑。为什么有效?感谢
答案 0 :(得分:1)
通配符是Set
的类型参数,而不是Test
。这里的语法是一个树状结构,其中每个类型参数都适用于它之外的类型。
Test<T>
↓
Set<E>
↓
? extends Object
NonWildcardTypeArguments
只要求每个类型参数都是ReferenceType
,Set<? extends Object>
满足,因为Identifier<TypeArgument>
形式。? extends Object
。 (TypeArgument
是ReferenceType
,但不是<Set<? extends Object>>
。)
例如,NonWildcardTypeArguments
是<? extends Set<Object>>
但NonWildcardTypeArguments
不是。{/ p>
是的,有一个通配符&#34;&#34;类型参数,但它嵌套在树中的一个级别。 4 + 1 = 5
构造只关心它内部的参数。
无论如何,正如assylias指出的那样,这种语法结构似乎不再存在,但我认为解释仍然很有趣。 (我尝试在JLS 8 PDF中搜索&#39; NonWildcardTypeArguments&#39;并且没有提出任何建议。)