ArrayList <superclass>中的SubClass对象是否保留SubClass独有的方法?</superclass>

时间:2013-11-30 02:02:53

标签: java inheritance arraylist

基本上标题是什么,但有些细节。我有一个带有几个SubClasses的SuperClass。我需要一个ArrayList来保存两种类型的子类,因此需要类型为SuperClass的ArrayList。我尝试使用getQuantity()访问Subclass1的ArrayList.get(0).getQuantity();方法(假设索引0的类型为SubClass1)。我收到错误:类型SuperClass的getQuantity未定义。

当放入SuperClass ArrayList时,SubClass对象是否不保留其属性?如果他们确实保留了他们的属性,我该如何访问它们?

3 个答案:

答案 0 :(得分:5)

对象本身仍然是subclass,但是当你将它们从集合中取出时它只知道superclass所以它无法告诉你哪个是哪个,它必须选择共同点。

如果您确切知道特定索引包含Subclass类型的对象,则可以将其强制转换:

Subclass myObject = (Subclass) list.get(0);
System.out.println(myObject.getQuantity());

它应该有用。

更安全的方法需要测试对象是否真的如你所想:

SuperClass myObject = list.get(0);
if ( myObject instanceof Subclass) {
  Subclass mySubObject = (Subclass) myObject;
  System.out.println(mySubObject.getQuantity());
}

如果对象不是Subclass类型,则第一个示例引发异常,第二个示例因为之前的测试而无法确认。

您需要了解的是SuperClass myObject = list.get(0)不是对象本身,而是访问内存中对象的引用。把它想象成一个允许你控制对象的遥控器,在这种情况下,它不是一个功能齐全的遥控器,因为它没有显示你的所有对象都能做到的,所以你可以切换到更好的一个(如{ {1}})能够访问所有功能。

我肯定会推荐Head First Java book因为它非常详细地介绍了这些内容(我从那里偷走了这个远程示例)。

答案 1 :(得分:0)

所有对象都保留自己的类标识,但使用ArrayList的代码并不直接知道它。就它而言,ArrayList只保存对SuperClass - 类型对象的引用,并且它只能在它从它检索的对象上调用SuperClass的方法。

调用代码可以使用instanceof或类似技术来查明集合中的特定对象是否属于子类型,但这通常是不好的做法,因为它通常表示混合不同抽象层次。通常认为合理的一种情况是,如果子类具有一些可选的高性能特性,调用者可以利用该特性(并且测量已确定值得使代码复杂化);一个例子可能是虽然List的{​​{1}}方法没有性能保证,但某些实现(如get())也实现了ArrayList,这表明没有性能损失以任何顺序使用RandomAccess

答案 2 :(得分:0)

当你有一些ArrayList并且你用扩展SuperClass的东西填充它时,你必须检查instanceof并强制转换以获取特定于这些子类的方法。

示例:

ArrayList<Animal> animals = new ArrayList<Animal>;
animals.add(new Duck());
animals.add(new Cow());
animals.add(new Horse());

for (Animal animal : animals) 
   if (animal instanceof Horse) {
      Horse horse = (Horse)animal;
      horse.gallop();
   }