{ "cells": [ { "cell_type": "markdown", "metadata": {}, "source": [ "# Template Pattern\n", "1. Usefull for encapsulating algorithms that follow similar steps, like a recipe\n", "1. Behavioral Pattern\n", "1. Defines algorithm's skeleton\n", "1. Order of methods is fixed inside the Template Method\n", "1. Best Code Reuse\n", "1. Allows hooking into algorithm\n", "1. But useless in case the algorithms differ\n", "1. **Comparable to Builder**, which is all about construction of objects, whereas Template is all about definition of objects behavior\n", "\n", "> **Constitutes 3 Methods**\n", "> - **Abstract** - Must be implemented by subclasses\n", "> - **Concrete** - Common enough, that subclass will be okay using the default implementation, can be overriden\n", "> - **Hooks** - Do nothing, but can be overriden to do something" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "# Travel" ] }, { "cell_type": "code", "execution_count": 1, "metadata": { "collapsed": true }, "outputs": [], "source": [ "from abc import ABCMeta, abstractmethod" ] }, { "cell_type": "code", "execution_count": 2, "metadata": { "collapsed": true }, "outputs": [], "source": [ "class ITransport(metaclass=ABCMeta):\n", " def __init__(self, destination):\n", " self._destination = destination\n", " \n", " def take_trip(self): # Template Method\n", " self.start_engine()\n", " self.leave_terminal()\n", " self.entertainment()\n", " self.travel_to_destination()\n", " self.arrive_at_destination()\n", " \n", " @abstractmethod\n", " def start_engine(self): # Abstract, must be implemented in subclass\n", " pass\n", " \n", " def leave_terminal(self): # Concrete, but overridable\n", " print(\"Leaving Terminal\")\n", " \n", " @abstractmethod\n", " def travel_to_destination(self): # Abstract, must be implemented in subclass\n", " print(\"Travelling ...\")\n", " \n", " def entertainment(self): # Hook, concrete but has no implementation\n", " pass\n", " \n", " def arrive_at_destination(self): # Concrete, but overridable\n", " print(f\"Arriving at {self._destination}\")" ] }, { "cell_type": "code", "execution_count": 3, "metadata": { "collapsed": true }, "outputs": [], "source": [ "class Airplane(ITransport):\n", " def start_engine(self):\n", " print(\"Starting the Rolls-Royce Gas-Turbine Engines\")\n", " \n", " def leave_terminal(self):\n", " print(\"Leaving Terminal\")\n", " print(\"Taxiing the Runway\")\n", " \n", " def travel_to_destination(self):\n", " print(\"Flying ...\")\n", " \n", " def entertainment(self):\n", " print(\"Playing in-flight movie\")\n", " \n", " \n", " def arrive_at_destination(self):\n", " print(f\"Landing at {self._destination}\")" ] }, { "cell_type": "code", "execution_count": 4, "metadata": { "collapsed": true }, "outputs": [], "source": [ "class Bus(ITransport):\n", " def start_engine(self):\n", " print(\"Starting the Cummins Diesel Engine\")\n", " \n", " def travel_to_destination(self):\n", " print(\"Driving ...\")" ] }, { "cell_type": "code", "execution_count": 5, "metadata": { "collapsed": true }, "outputs": [], "source": [ "def travel(destination, transport):\n", " print(f\"\\n=============== Taking the {transport.__name__} to {destination} ===============\\n\")\n", " \n", " transport(destination).take_trip()" ] }, { "cell_type": "code", "execution_count": 6, "metadata": {}, "outputs": [ { "name": "stdout", "output_type": "stream", "text": [ "\n", "=============== Taking the Bus to New York ===============\n", "\n", "Starting the Cummins Diesel Engine\n", "Leaving Terminal\n", "Driving ...\n", "Arriving at New York\n", "\n", "=============== Taking the Airplane to Amsterdam ===============\n", "\n", "Starting the Rolls-Royce Gas-Turbine Engines\n", "Leaving Terminal\n", "Taxiing the Runway\n", "Playing in-flight movie\n", "Flying ...\n", "Landing at Amsterdam\n" ] } ], "source": [ "travel('New York', Bus)\n", "travel('Amsterdam', Airplane)" ] } ], "metadata": { "kernelspec": { "display_name": "Python 3", "language": "python", "name": "python3" }, "language_info": { "codemirror_mode": { "name": "ipython", "version": 3 }, "file_extension": ".py", "mimetype": "text/x-python", "name": "python", "nbconvert_exporter": "python", "pygments_lexer": "ipython3", "version": "3.6.3" } }, "nbformat": 4, "nbformat_minor": 2 }