阴影还是实施?

时间:2013-06-26 14:51:35

标签: java methods interface override shadowing

public class SuperClass {
    public void doFoo() {
        //...
    }
}

public class SubClass extends SuperClass implements AnInterface {}

public interface AnInterface {
    public abstract void doFoo();
}

为什么SubClass不必实施doFoo()方法?我想这是因为它已经在它的超类中了。但我无法在@Override中为doFoo()方法添加SuperClass。它被遮蔽了吗?或者叫什么?这是一个很好/正常的做法吗?

3 个答案:

答案 0 :(得分:1)

一般来说,你所做的事情并没有错。子类从父类继承doFoo方法,从而满足接口强加的要求。

如果您希望您的代码过于清晰(可能有助于将来的维护),可以选择一个选项:

public class SubClass extends SuperClass implements AnInterface {

  @Override
  public void doFoo() {
    super.doFoo();
  }
}

我不确定您的原始问题是否有特定的术语。也许“轻微混淆遗产”?

答案 1 :(得分:1)

  

为什么SubClass不必实现doFoo()方法?

因为它已在SuperClass中实现。

  

但我不能在SuperClass中为doFoo()方法添加@Override。

不,你不能,因为SuperClass没有实现AnInterface。它不会覆盖任何人的方法。

  

所以它被遮蔽了吗?

没有。遮蔽是另一回事。它涉及变量。因此,如果SuperClass具有可变foo,则在SubClass中您尝试定义具有相同名称的变量,即 shadowing 。这没有名字。

  

这是一个很好/正常的做法吗?

这是正常做法。我在很多大项目中都多次见过它。



TLDR示例如下

假设我们有一个实现ModelBasedWizard所需的界面(向导在许多桌面应用程序中很常见)。

public interface IModelBasedWizard {

    public void addWizardPage(IWizardPage page);

    public IStatus getWizardStatus();

    public void bindModel(IModel model);
}

假设已经有一个向导的实现

public class Wizard {

    public void addWizardPage(IWizardPage page) {
        pages.add(page);
        page.createContent(this);
    }

    public IStatus getWizardStatus() {
        List<IStatus> stati= new ArrayList<Status>();
        for (IWizardPage page : pages) {
            stati.add(page.getStatus());
        }
        return stati;
    }
}

现在,这只是向导的视觉部分,但它对模型一无所知。好的,没问题:

public class ModelBasedWizard extends Wizard implements IModelBasedWizard {
    //UI, pages, stati and all other functionalities are already implemented.
    //I just need to bind this wizard to a model

    //create some content here

    @Override
    public void bindModel(IModel model) {
        this.model = model;
        this.fieldOne.bindToModel(model);
        model.addPropertyChangeListener(new PropertyChangeListener() {
            //bla bla
        });
    }
}

答案 2 :(得分:0)

这是接口的使用方式。当您实现一个接口时,所有关于该类的更改都是您需要在类中具有由该接口定义的方法。

要使代码工作所需要做的就是在子类中放置一个名为doFoo()的空方法。