読者です 読者をやめる 読者になる 読者になる

【デザインパターン】Template Method

デザインパターン

どんなもの?

  • 処理の手順を基本クラスに定義しておく。

(Placeholdersを宣言する)

  • その中の派生クラスによって差異部分となる処理を派生クラスで実装する。

(Placeholdersを実装する)

どんなときに使う?

大まかな処理が共通で、アルゴリズムの具体的な設計を様々変化させたいときに使う。
大まかな処理は基本クラスに定義し、そのクラスを継承する派生クラスに差異部分を記述する。

利点は?

  • 共通部分を何度も記述しなくて良くなる
  • 共通部分の変更の際には、基本クラスに変更を加えるだけで、対応可能

欠点は?

典型的な構成要素

  • AbstarctClass
  • ConcreteClass

コード

  1. アルゴリズムの手順を基本クラスの「Template method」の中に標準化
  2. 差異部分として実装が必要な処理を基本クラスの中にplaceholdersとしておく
  3. 派生クラスでplaceholdersを実装
#include <iostream>
using namespace std;

class Base
{
    void a()
    {
        cout << "a  ";
    }
    void c()
    {
        cout << "c  ";
    }
    void e()
    {
        cout << "e  ";
    }
    // 差異部分として実装が必要な処理を基本クラスの中にplaceholdersとしておく
    virtual void ph1() = 0;
    virtual void ph2() = 0;
  public:
    // アルゴリズムの手順を基本クラスの「Template method」の中に標準化
    void execute()
    {
        a();
        ph1();
        c();
        ph2();
        e();
    }
};

class One: public Base
{
    // 派生クラスでplaceholdersを実装
    void ph1()
    {
        cout << "b  ";
    }
    void ph2()
    {
        cout << "d  ";
    }
};

class Two: public Base
{
    void ph1()
    {
        cout << "2  ";
    }
    void ph2()
    {
        cout << "4  ";
    }
};

int main()
{
  Base *array[] = 
  {
     &One(), &Two()
  };
  for (int i = 0; i < 2; i++)
  {
    array[i]->execute();
    cout << '\n';
  }
}