どうも、とがみんです。
「オブジェクト指向における再利用のためのデザインパターン」という本を参考にしつつ、TemplateMethodパターンについて調べたのでまとめていきます。
TemplateMethodパターンとは?
TemplateMethodパターンとは、テンプレートの機能を提供するパターンです。抽象クラスで処理の枠組みを定めテンプレートとし、具体クラスでその具体的な内容を実装します。
TemplateMethodパターンのメリットとしては、「具体クラスの実装の単純化」、「メソッドの共通化による保守性の向上」が挙げられます。
アルゴリズムの不変な部分を抽象クラスに実装し、振る舞いが変わりえる部分の実装は具体クラスで行うことで、具体クラスの実装を単純化することができます。
また、同じコードがいたるところに現れることがないように、具体クラス間で共通の振る舞いをする部分を抜き出して、これを共通のクラス(抽象クラス)に局所化し、テンプレートとすることによって、
不具合が発覚した場合は、抽象クラスのテンプレートメソッド内のロジックを修正するだけでよくなりプログラムの保守性が高まります。
TemplateMethodパターンの構成要素とサンプル
TemplateMethodパターンは「抽象クラス」と「具体クラス」で構成されています。
「抽象クラス」には、抽象的なメソッドを定義し、アルゴリズムの骨格、テンプレートとなる具体クラス間で共通の振る舞いをする部分を記述し、「具体クラス」には処理の詳細を記述します。
以下にグリルフードを作成するサンプルについて紹介します。
抽象クラスの作成
グリルフードの料理手順の枠組みとして、以下のように考えます。
- 材料を準備する
- 材料を焼く
- 焼いた材料を配置する
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 | public abstract class CookGrilledFood { //材料の準備 public abstract void prepareIngredients(Food food); //材料を焼く public abstract void grillIngredients(Food food); //材料を並べる public abstract void arrangementIngredients(Food food); //グリルフードを作成する手順のテンプレート public void cookGrilledFood(){ Food food = new Food(); prepareIngredients(food); System.out.println(food.getStatus() + " : " + food.getIngredientsName()); grillIngredients(food); System.out.println(food.getStatus() + " : " + food.getIngredientsName()); arrangementIngredients(food); System.out.println(food.getStatus() + " : " + food.getIngredientsName()); } } |
具体クラスの作成
抽象クラスには、グリルフードを作成するための処理の骨格を記述しました。
具体クラスでは、抽象クラスで定義した抽象メソッドの具体的な処理を記述します。
どのような材料を準備して、そのように材料を焼いて、どのように配置するかといった具体的な処理を記述します。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 | public class CookGrilledChiken extends CookGrilledFood { public void prepareIngredients(Food food){ food.setStatus("材料を購入しました"); food.getIngredients().add("チキン"); food.getIngredients().add("ブロッコリー"); } public void grillIngredients(Food food){ food.setStatus("200度の温度で15分焼きました"); } public void arrangementIngredients(Food food){ food.setStatus("高級感あるお皿に配置しました"); } } |
処理の実行
1 2 3 4 5 6 7 8 | public static void main(String[] args) { SpringApplication.run(TemplateMethodApplication.class, args); //グリルチキンの作成 CookGrilledFood grilledChiken = new CookGrilledChiken(); grilledChiken.cookGrilledFood(); } |
実行結果
200度の温度で15分焼きました : チキン ブロッコリー
高級感あるお皿に配置しました : チキン ブロッコリー
まとめ
TemplateMethodパターンについてまとめてきました。
抽象クラスに、アルゴリズムの骨格であるテンプレートとなるメソッドを定義し、具体処理を具体クラスに記述することによって、「具体クラスの実装の単純化」や「メソッドの共通化による保守性の向上」といったメリットがあります。
サンプルコードはgithubに挙げておいたので参考になれば。