获取Super的属性值而不是实际对象

时间:2015-06-05 21:26:08

标签: java inheritance

我有以下内容:

Public Abstract class Entity
  protected int damagePoints = 0;

  public getDamagePoints() {
     return this.damagePoints;
  }

Public abstract class IA extends Entity

Public class Zombie extends IA implements Attacker {
    protected int damagePoints = 40;
}

Public class Engineer extends Entity implements DamageReceiver;

Public interface Attacker {
   public attack(Entity entity);
}

Public interface DamageReceiver {
   public receiveDamage(Attacker entity)
}

Engineer类重写了这个方法:

@Override
    public void receiveDamage(Attacker entity) {
        if (entity instanceof Zombie) {
            int damagePoints = ((Zombie) entity).getDamagePoints();
            this.setHealthPoints(this.getHealthPoints() - damagePoints);
        }
    }

现在我有一个工程师实例化,还有一个Zombie。 当我Zombie.attack(engineer)时,我在工程师班的receiveDamage()中设置了一个断点,我认为damagePoints0

为什么会发生这种情况的任何线索?这是因为我复制了属性damagePoints吗?如果是这样,我如何让Zombie拥有40个伤害点,而不是在所有构造函数中重复this.damagePoints = 40

enter image description here

3 个答案:

答案 0 :(得分:2)

您在damagePoints中重新声明了Zombie,希望getDamagePoints()中的Entity能够在Zombie中获取新值,但就像您一样看来,它没有。在Java中,多态性与方法调用一起使用,但不与变量一起使用。 damagePoints中的Entity变量是getDamagePoints()方法的范围变量,因此从0的{​​{1}}变量返回Entity

要在damagePoints中返回40,您无需重新声明另一个同名变量,隐藏 Zombie变量damagePoints,但您可以覆盖Entity中的getDamagePoints()方法。你不需要一个变量,更不用说同名变量了(除非你计划在游戏中改变数量)。在Zombie

Zombie

您甚至可能希望@Override public int getDamagePoints() { return 40; } 方法在getDamagePoints()中为abstract,从而强制子类实现该方法。这意味着Entity中不需要变量damagePoints

Entity

答案 1 :(得分:0)

这种情况正在发生,因为当你调用getDamagePoints时,它会返回抽象类Entity的damagePoints值,而不是已经扩展它的类。通过使Entity的getDamagePoints方法为abstract来解决此问题,并为每个扩展类提供实现。

答案 2 :(得分:0)

看来Zombie有多个构造函数,所有构造函数都需要初始化damagePoints以避免重复代码,包括可能重复方法getDamagePoints。

解决方案是使用"这个"将建设者联系在一起。例如,如果一个构造函数为每个其他构造函数获取参数的超集,则执行其中的实际工作:

public Zombie(/* some subset of parameters */){
  this(/* full set of parameters with defaults filled in */);
}

public Zombie(/* full set of parameters */){
  damagePoints = 40;
  /* rest of initialization */
}

如果没有常见的超集构造函数,你仍然可以使用"这个"做共同的工作。您可能需要使用特殊的私有构造函数:

private Zombie(boolean special) {
  damagePoints = 40;
}

public Zombie() {
  this(true);
  /* Rest of the constructor */
}