Template method
From Wikibooks, open books for an open world
Define the skeleton of an algorithm in an operation, deferring some steps to subclasses. Template Method lets subclasses redefine certain steps of algorithm without changing the algorithm's structure.
Implementation in Java
/** * An abstract class that is common to several games in * which players play against the others, but only one is * playing at a given time. */ abstract class Game { protected int playersCount; abstract void initializeGame(); abstract void makePlay(int player); abstract boolean endOfGame(); abstract void printWinner(); /* A template method : */ public final void playOneGame(int playersCount) { this.playersCount = playersCount; initializeGame(); int j = 0; while (!endOfGame()) { makePlay(j); j = (j + 1) % playersCount; } printWinner(); } }
// Now we can extend this class in order // to implement actual games: class Monopoly extends Game { /* Implementation of necessary concrete methods */ void initializeGame() { // Initialize players // Initialize money } void makePlay(int player) { // Process one turn of player } boolean endOfGame() { // Return true if game is over // according to Monopoly rules } void printWinner() { // Display who won } /* Specific declarations for the Monopoly game. */ // ... }
import java.util.Random; class SnakesAndLadders extends Game { /* Implementation of necessary concrete methods */ void initializeGame() { // Initialize players playerPositions = new int[playersCount]; for (int i = 0; i < playersCount; i++) { playerPositions[i] = 0; } die = new Random(); winnerId = -1; } void makePlay(int player) { // Roll the die int dieRoll = die.nextInt(6) + 1; // Move the token playerPositions[player] += dieRoll; // Move up or down because of the ladders or the snakes int penaltyOrBonus = board[playerPositions[player]]; playerPositions[player] += penaltyOrBonus; if (playerPositions[player] > 8) { // Has reached the top square winnerId = player; } } boolean endOfGame() { // The game is over when a winner exists return (winnerId != -1); } void printWinner() { System.out.println("Player #" + winnerId + " has won!"); } /* Specific declarations for the Snakes and Ladders game. */ // The board from the bottom square to the top square // Each integer is a square // Negative values are snake heads with their lengths // Positive values are ladder bottoms with their heights private static final int[] board = {0, 0, -1, 0, 3, 0, 0, 0, -5, 0}; // The player positions // Each integer represents one player // The integer is the position of the player (index) on the board private int[] playerPositions = null; private Random die = null; private int winnerId = -1; }
Implementation in C#
using System; class MainApp { static void Main() { AbstractClass c; c = new ConcreteClassA(); c.TemplateMethod(); c = new ConcreteClassB(); c.TemplateMethod(); // Wait for user Console.Read(); } } // "AbstractClass" abstract class AbstractClass { public abstract void PrimitiveOperation1(); public abstract void PrimitiveOperation2(); // The "Template method" public void TemplateMethod() { PrimitiveOperation1(); PrimitiveOperation2(); Console.WriteLine(""); } } // "ConcreteClass" class ConcreteClassA : AbstractClass { public override void PrimitiveOperation1() { Console.WriteLine("ConcreteClassA.PrimitiveOperation1()"); } public override void PrimitiveOperation2() { Console.WriteLine("ConcreteClassA.PrimitiveOperation2()"); } } class ConcreteClassB : AbstractClass { public override void PrimitiveOperation1() { Console.WriteLine("ConcreteClassB.PrimitiveOperation1()"); } public override void PrimitiveOperation2() { Console.WriteLine("ConcreteClassB.PrimitiveOperation2()"); } }