3

次の問題に直面しています。

サブクラスで実装する必要がある public の generate、clone などのメソッドを含む抽象クラスを定義しました。ただし、これらのパブリック メソッドが呼び出されたときに、他の特定のメソッドも抽象クラス内で実行されるようにしたいと考えています。

明らかな解決策は、保護された抽象メソッドを実装し、抽象メソッドと必要な他のすべてのメソッドを呼び出すパブリック非抽象メソッドを作成することです。

例えば:

abstract class Representation {

    public void generate(int variable) {
        myFunction();
        generateAbstract(variable);
    }

    protected abstract void generateAbstract(int variable);

    private void myFunction() {
        //do something
    }
}

私の質問は、それをより良い方法で解決する方法、またはこれがユーザーフレンドリーな方法で関数に名前を付ける方法である場合です。

ありがとう!

4

6 に答える 6

5

この問題を解決するあなたの方法は非常に標準的であるため、名前さえあります。それはTemplate Method Patternと呼ばれます。アイデアは、高レベルでアルゴリズムのステップを実行するパブリック メソッドを提供し、サブクラスで保護された抽象メソッドのオーバーライドを使用して、アルゴリズムの低レベルのステップを処理することです。これは、問題に対処する正しい方法です。

于 2012-07-31T13:22:01.773 に答える
3

あなたがやっているように、私はそれをします。ラッパーメソッドを作成します

  1. finalだから私はサブクラスで吹き飛ばされることはありません、または
  2. 抽象メソッドを呼び出さなければならないことを示して、メソッドのすべてを文書化します...
于 2012-07-31T13:21:29.987 に答える
1

@dasblinkenlight の回答は、問題に対処するデザイン パターンを特定します: テンプレート メソッド。参照に答えるウィキペディアのエントリよりも、このテンプレートメソッドのリンクが好きです。また、コード例を含む回答が好きです:

// Demonstrate the template method design pattern
// straight out of GoF example
abstract class AbstractClass {
    // Final ensures extender does not override, but depends on your design
    final void templateMethod() {
        primitiveOperation1();
        primitiveOperation2();
    }

    // document extenders should keep as protected
    // so clients do not call directly
    protected abstract void primitiveOperation1();
    protected abstract void primitiveOperation2();
}

public class ConcreteClass extends AbstractClass {
    @Override
    protected void primitiveOperation1() {
        System.out.println("ConcreteClass.primitiveOperation1()");
    }

    @Override
    protected void primitiveOperation2() {
        System.out.println("ConcreteClass.primitiveOperation2()");
    }
}
于 2012-07-31T13:48:59.440 に答える
0

super.generateこれを行う最も簡単な方法は、それが確実に呼び出されるようにすることだと思います。Java には、いつサブクラス化されたかをクラスに通知するための適切なメカニズムがないため (Ruby などはそうです)、抽象メソッドを実装するサブクラスに別のメソッドを呼び出すように強制するためにできることはあまりありません。

于 2012-07-31T13:24:40.977 に答える
0

前に指摘したように、あなたが提案したのはTemplate method patternによる正しいアプローチです。残るはネーミングの問題。上書きされる関数を「generateAbstract」とは呼びません。実装すると抽象的でなくなるからです。元の関数を反映し、それが何をするかを暗示する「makeGenerate()」のようなものをお勧めします。

abstract class Representation {

  public void generate(int variable) {
    myFunction();
    makeGenerate(variable);
  }

  protected abstract void generateAbstract(int variable);

  private void myFunction() {
    //do something
  }
}

public class ConcreteClass extends Representation {
  @Override
  protected void makeGenerate() {
    ...
  }
于 2012-07-31T14:07:26.603 に答える
0

あなたが提案した方法は非常にエレガントだと思います。私は確かに以前にこの方法で同じ問題を解決しました。私はおそらくあなたのメソッドdoGenerate()(または単語Abstractが含まれていないもの)を呼び出すでしょう。

于 2012-07-31T13:20:58.130 に答える