Ric*_*ral 27 java generics wildcard
我几天前从未听说过野猫,在读完老师的Java书后,我仍然不确定它是什么,为什么我需要使用它.
比方说,我有一个超类Animal和几个子类,如Dog,Cat,Parrot,等...现在我需要有动物名单,我首先想到的会是这样的:
List<Animal> listAnimals
Run Code Online (Sandbox Code Playgroud)
相反,我的同事们推荐的内容如下:
List<? extends Animal> listAnimals
Run Code Online (Sandbox Code Playgroud)
为什么我应该使用通配符而不是简单的泛型?
假设我需要一个get/set方法,我应该使用前者还是后者?他们怎么这么不同?
Ale*_*yak 24
声明局部变量时,通配符没有多大意义,但是在为方法声明参数时它们非常重要.
想象一下你有一个方法:
int countLegs ( List< ? extends Animal > animals )
{
int retVal = 0;
for ( Animal cur : animals )
{
retVal += cur.countLegs( );
}
return retVal;
}
Run Code Online (Sandbox Code Playgroud)
使用此签名,您可以执行以下操作:
List<Dog> dogs = ...;
countLegs( dogs );
List<Cat> cats = ...;
countLegs( cats );
List<Animal> zoo = ...;
countLegs( zoo );
Run Code Online (Sandbox Code Playgroud)
但是,如果你这样声明countLegs:
int countLegs ( List< Animal > animals )
Run Code Online (Sandbox Code Playgroud)
然后在前面的例子中只会countLegs( zoo )编译,因为只有那个调用具有正确的类型.
pol*_*nts 22
Java泛型是不变的.
假设我们有B extends A:
B 是一个子类型 Ainstanceof B也是一个instanceof A由于Java数组是协变的:
B[] 是一个子类型 A[]instanceof B[]也是一个instanceof A[]但是,Java泛型是不变的:
List<B> 不是的子类型 List<A>instanceof List<B>不是instanceof List<A>.通配符用于使其更灵活,同时保持类型安全.
List<B>是一个List<? extends A>List<Animal> animals = new ArrayList<Dog>()?<E extends Number>和之间有什么区别<Number>?您的两个示例之间的区别仅在于第一个是通用/一般动物的列表 - 因此您可以向其添加任何类型的动物,以及Animal类型的子类的任何实例.(例如,它可以包含一些狗,一些猫,一些豪猪...)而第二个List <? extends Animal>- 将是一个特定的类动物亚型的列表.它可以是您选择的任何一个(每次在运行时设置),但只有一个.它将要么是狗的列表,或猫的列表,或海龟的列表...等等.
| 归档时间: |
|
| 查看次数: |
1811 次 |
| 最近记录: |