回归collections vs Collection
这两种方法有什么区别?
Collection getTypes();
VS
Collection getTypes();
如果Type是类或接口,这是否重要? 特别是,在设计API时,首选哪个版本以及为什么?
Collection getTypes();
这里, getTypes()
必须返回Collection
(例如ArrayList
或HashSet
)。
Collection extends Type> getTypes();
这里, getTypes()
可以返回任何属于或扩展Type
的Collection
(例如, ArrayList
或HashSet
)。 因此,从第一个变量返回的任何内容也可以从第二个变量返回。 但是,在第二个中,您不知道集合的类型参数究竟是什么; 你只知道它扩展了Type
。
至于哪个应该是首选,它实际上取决于你想要做什么,以及什么在逻辑上更有意义。 请记住,当你有 extends Type>
extends Type>
,你其实不知道什么?
是的,这有时会阻碍; 通常情况下,第一种变体更适合。 您可以在基类中使用第二个变体,并在子类中使用与第一个类似的东西覆盖它,例如:
@Override Collection getTypes() { ... }
通常不鼓励使用通配符类型返回,请参阅generics常见问题解答中的详细原因。 简而言之,它可以使返回的对象变得无用(或不太有用),因为使用类型参数的参数的方法只能使用’null’来调用。 例如,使用Collection
:
Collection extends Type> collection = ... collection.add(null); // OK collection.add(anInstanceOfType); // Error
在这种情况下,这可以防止向集合添加任何东西(这不是坏事,似乎有人使用它来尝试使返回的集合“只读”, 这里 ),但一般来说这可能会导致问题。
extends Type>
extends Type>
是一个边界通配符generics。 以这种方式定义的集合可以是任何类型或Type
子类。 即。
Collection typeCollection; //or Collection subtypeCollection; //where subtype is... class SubType extends Type
在这种情况下最重要的是?
属于Type
。
Collection
必须返回Type
的集合。 即。
Collection collection;
阅读这里的教程。 欲获得更多信息。 您选择的将取决于您的需求。
这是一个例子。 在定义可渲染项目组时,我使用有界通配符。 例如。
public class SpriteGroup
这将是Sprite的集合,或Sprite的任何子类。 这很有用,因为我可以像这样定义组:
SpriteGroup physicalSprites = new SpriteGroup (); PhysicalSprite physicalSprite = physicalSprites.get(0); SpriteGroup particleSprite = new SpriteGroup (); ParticleSprite particle = particleSprite.get(0);
任何get / set例程然后返回我指定的类型(PhysicalSprite,ParticleSprite),这是可取的。
如果我将其定义为:
SpriteGroup spriteGroup = new SpriteGroup(); //all I can retrieve is a sprite, gotta cast now... Sprite sprite = spriteGroup.get(0);
我需要将它们转换为访问特定于每种类型Sprite的属性。 SpriteGroup
类都将受到同样的限制。