Deze presentatie volgt nauw de bovengenoemde bijbel. Gedurende de komende weken zal de lijst met voorbeelden worden uitgebreid.
Daarbij kun je onderscheid maken tussen de scoop en het doel.
Heel vaak zijn er meerdere Patterns tegelijk en door elkaar aanwezig. Juist dan is het goed deze te benoemen, daarmee wordt de code doorzichtig. Patterns maken het de code ook herbruikbaar, omdat de variatie die er is, of te verwachten is, is ingebed in de pattern structuur.
Welke Patterns zijn er dan? Hier een aantal benoemde, maar er zijn er ongetwijfeld meer. Kijk maar eens in je eigen software en probeer ze aan te wijzen. Kom je regelmatige een structuur tegen die er niet tussen staat, dan heb je vast een nieuwe te pakken.
Creational Patterns
Structural Patterns
Behavioral Patterns
Creational Patterns
Structural Patterns
Behavioral Patterns
Het Singleton zorgt ervoor dat er van een bepaalde classe maar een (1) instantie bestaat.
Van sommige objecten is er maar een nodig of wenselijk of aanwezig.
Dit is taal afhankelijk:
Er is maar een instantie nodig/wenselijk
Definitie van een interface voor de creatie van een object, maar welke classe wordt geinstancieerd wordt bepaald door door een subclasse.
Het direct aanmaken van object is bij grotere systemen al gauw onoverzichterlijk of onmogelijk, indien we code herbruikbaar willen maken.
Hiervoor is het meestal nodig twee classen te maken, een factory en een basistype voor de gefabriceerde objecten. Van beide kan dan worden overerfd voor specifieke classen. De afgeleide factory is dan in staat het afgeleide basistype aan te maken. In Eiffel kan dat mooi met covariante methode overerving, bij Delphi en Java is typecasten nodig.
Het verstrekken van een interface voor de constructie van een familie van onderling afhankelijke objecten zonder de specifieke classe voor te schrijven.
Soms wil je een groep van objecten die samen een taak hebben vrij kunnen vervangen door een andere groep objecten die dezelfde taak anders invullen. Dan is het handig de classen hiervan abstract te definieren, en de gebruiker in het onwetende te laten welke concrete classen nu worden gebruikt.
Het scheiden van de constructie van een complex object van de representatie zdd hetzelfde constructieproces kan worden gebruikt voor meerdere representaties.
Maak een object aan dat model staat voor de hele serie objecten die je wilt aanmaken. De constructie van deze objecten geschied door het maken van een kopie.
Het opnieuw aanmaken van objecten en opvullen met waarden is niet altijd de meest effectieve manier. Hierbij kunnen classen betrokken zijn die niet bekend (zouden moeten ) zijn bij diegene die het object aanmaakt. Dan is een goede manier het maken van een copie vanuit een voorbeeld. Veel gebruikt bij het behandelen van xml documenten.
Het omzetten van een interface van een classe in een andere interface zodat deze door de client kan worden gebruikt. De adapter laat classen samenwerken die dat niet direct kunnen door incompatibele interfaces.
Classen die los van elkaar ontwikkeld worden passen vaak niet op elkaar een class adapter (wrapper) is dan nodig.
Het ontkoppelen van de abstractie van de implementatie zodat beide onfhankelijk kunnen worden ontwikkeld.
Wanneer de gebruikelijk wijze om deze ontkoppeling te realizeren (overerving) niet flexibel genoeg is een bridge handig. De abstractie wordt ontworpen aan de behoefte, de implementatie naar de mogelijkheden (bijvoorbeeld klassen die al voorhanden zijn)
Wanneer elementen op gelijk wijze gebruikt moeten kunnen worden als verzamelingen gebruik je een composite. Deze verpakt objecten in een boomstructuur zdd het voor de classen die ermee werken er geen verschil is tussen een enkel object of een container object.
Bijvoorbeeld in tekenprogramma's is het vaak zo dat objecten soms alleen en soms tegelijk moeten kunnen worden veranderd. Door de toepassingen van een composite kan dit gemakkelijk worden geimplementeerd.
Het dynamisch toevoegen van functies aan een object. Dit als aanvulling op overerving (is statisch)
Als je functies toevoegt door overerving worden deze meegegeven aan alle instanties van de nieuwe classe. Dat is niet altijd wenselijk. Daarom kun je ook kiezen voor het toevoegen aan objecten afzonderlijk.
Het object dat je wilt uitbreiden wordt ondergebracht in een decorator, waarvan de interface natuurlijk moet overeenkomen met die van het object zodat de gebruikers daar niets van merken. Het oorspronkelijke object moet gewoon kunnen worden gebruikt in de "oude" code.