如何创建"抽象领域"?

Jul*_*éon 8 java constructor abstract-class

我知道java中不存在抽象字段.我也读过这个问题,但提出的解决方案并不能解决我的问题.也许没有解决方案,但值得问:)

问题

我有一个抽象类,它根据其中一个字段的值在构造函数中执行操作.问题是该字段值将根据子类而改变.我该怎么做才能对子类重新定义的字段的值进行操作?

如果我只是"覆盖"子类中的字段,则对抽象类中字段的值进行操作.

我对任何确保在子类实例化期间完成操作的解决方案持开放态度(即将操作放在构造函数中每个子类调用的方法中都不是有效的解决方案,因为有人可能会扩展抽象类并忘记调用方法).

另外,我不想将字段的值赋予构造函数的参数.

有没有解决办法,或者我应该改变我的设计?


编辑:

我的子类实际上是我的主程序使用的一些工具,因此构造函数必须是公共的并且完全采用它们将被调用的参数:

tools[0]=new Hand(this);
tools[1]=new Pencil(this);
tools[2]=new AddObject(this);
Run Code Online (Sandbox Code Playgroud)

(子类是Hand,Pencil和AddObject,它们都扩展了抽象类Tool)

这就是我不想改变构造函数的原因.

我即将使用的解决方案是将上面的代码略微更改为:

tools[0]=new Hand(this);
tools[0].init();
tools[1]=new Pencil(this);
tools[1].init();
tools[2]=new AddObject(this);
tools[2].init();
Run Code Online (Sandbox Code Playgroud)

并使用抽象的getter访问该字段.

Cro*_*zin 13

对于字段的抽象getter/setter怎么样?

abstract class AbstractSuper {
    public AbstractSuper() {
        if (getFldName().equals("abc")) {
            //....
        }
    }

    abstract public void setFldName();
    abstract public String getFldName();
}

class Sub extends AbstractSuper {
    @Override
    public void setFldName() {
        ///....
    }

    @Override
    public String getFldName() {
        return "def";
    }
}
Run Code Online (Sandbox Code Playgroud)

  • 如果您不使用字段但将值直接作为"getter"的返回值(如给出的代码示例中那样)(这不再是正确的getter ...),这实际上是有效的.但是,谢谢,这比没有好如果没有其他答案,我会用它! (3认同)
  • 使用@Overrdie注释可能会危害您的应用程序的可编译性 (3认同)
  • 超级构造函数执行后初始化子类字段,因此这不会按预期工作. (2认同)

Mic*_*rdt 13

另外,我不想将字段的值赋予构造函数的参数.

为什么不?这是完美的解决方案.使构造函数protected不提供默认构造函数,子类实现者被迫在其构造函数中提供一个值 - 它可以是公共的并将常量值传递给超类,使得参数对子类的用户不可见.

public abstract class Tool{
    protected int id;
    protected Main main;
    protected Tool(int id, Main main)
    {
        this.id = id;
        this.main = main;
    }
}

public class Pencil{
    public static final int PENCIL_ID = 2;
    public Pencil(Main main)
    {
        super(PENCIL_ID, main);
    }
}
Run Code Online (Sandbox Code Playgroud)