DESIGN PATTERNS
By: DJOUABRI Abderrezak
STRUCTURAL
PATTERNS
Adapter. Bridge. Composite. Decorator.
Facade. Flyweight. proxy.
Adapter
pattern
Convertit une interface
en une autre
Intent
■ Convert the interface of a class into
another interface clients expect.
■ Adapter lets classes work together
that couldn't otherwise because of
incompatible interfaces.
Also Known As
Wrapper
Fonctionnement
Les adaptateurs aide des objets avec différentes
interfaces à collaborer. Voilà comment cela fonctionne:
■ L'adaptateur obtient une interface, compatible avec
l'un des objets existants.
■ À l'aide de cette interface, l'objet existant peut appeler
en toute sécurité les méthodes de l'adaptateur.
■ Lors de la réception d'un appel, l'adaptateur transmet
la demande au deuxième objet, mais dans un format
et dans l'ordre que le deuxième objet attend.
xample
Imaginez que vous créez une application de
surveillance des marchés boursiers. L'application
télécharge les données boursières de plusieurs
sources au format XML, puis affiche de jolis graphiques
et diagrammes pour l'utilisateur.
À un moment donné, vous décidez d'améliorer
l'application en intégrant une bibliothèque d'analyse
intelligente tierce. Mais il y a un souci : la bibliothèque
d'analyse ne fonctionne qu'avec des données au
format JSON.
Vous ne pouvez pas utiliser la bibliothèque d'analyse
«telle quelle», car elle attend les données dans un
format incompatible avec votre application.
Vous pouvez modifier la bibliothèque
pour qu'elle fonctionne avec XML.
Cependant, cela pourrait casser du
code existant qui repose sur la
bibliothèque. Et pire encore, vous
n’avez peut-être pas accès au code
source de la bibliothèque, ce qui rend
cette approche impossible.
Solution
■ Vous pouvez créer un adaptateur. Il s'agit d'un
objet spécial qui convertit l'interface d'un
objet afin qu'un autre objet puisse le
comprendre.
■ Un adaptateur enveloppe l'un des objets pour
masquer la complexité de la conversion qui se
produit en arrière-plan. L'objet enveloppé n'est
même pas au courant de l'adaptateur,
S tructure
Participants
Target Interface: This is the desired interface class
which will be used by the clients.
Adapter class: This class is a wrapper class which
implements the desired target interface and
modifies the specific request available from the
Adaptee class.
Adaptee class: This is the class which is used by the
Adapter class to reuse the existing functionality and
modify them for desired use.
Client: This class will interact with the Adapter class.
Object adapter
Object adapter
The Client is a class that
contains the existing
business logic of the
program.
Object adapter The Client Interface
describes a protocol that
other classes must follow
to be able to collaborate
with the client code.
Object adapter The Service is some useful
class (usually 3rd-party or
legacy). The client can’t use
this class directly because it
has an incompatible interface.
Object adapter The Adapter is a class that’s
able to work with both the
client and the service: it
implements the client
interface, while wrapping the
service object. The adapter
receives calls from the client
via the adapter interface and
translates them into calls to
the wrapped service object in a
format it can understand.
Object adapter The client code doesn’t get coupled to
the concrete adapter class as long as
it works with the adapter via the client
interface. Thanks to this, you can
introduce new types of adapters into
the program without breaking the
existing client code. This can be
useful when the interface of the
service class gets changed or
replaced: you can just create a new
adapter class without changing the
client code.
Class adapter
Class adapter
The Class Adapter doesn’t
need to wrap any objects
because it inherits behaviors
from both the client and the
service. The adaptation
happens within the
overridden methods. The
resulting adapter can be
used in place of an existing
client class.
xample
Considérons un scénario dans lequel il existe
une application qui renvoie la vitesse des
voitures de luxe en miles par heure (MPH).
Maintenant, nous devons utiliser la même
application pour notre client qui veut les
mêmes résultats mais en kilomètres par heure
(km / h).
Pour résoudre ce problème, nous allons créer
un adaptateur qui convertira les valeurs et
nous donnera les résultats souhaités:
Composite
pattern
Composer des objets en
structures arborescentes
(structures d'arbres)
Intent
Compose objects into tree structures
(structures d'arbres) to represent part-whole
hierarchies (hiérarchies partielles) .
Composite lets clients treat individual objects
and compositions of objects uniformly
(permet de traiter les objets individuels et
composés de manière uniforme).
xample
Les armées de la plupart des pays sont structurées en
hiérarchies. Une armée se compose de plusieurs
divisions; une division est un ensemble de brigades, et
une brigade se compose de sections qui peuvent être
décomposés en équipes. Enfin, une équipes est un petit
groupe de vrais soldats. Les ordres sont donnés au
sommet de la hiérarchie et transmis à chaque niveau
jusqu'à ce que chaque soldat sache ce qui doit être fait.
An example of a military structure.
xample
Motivation
Les applications graphiques comme les
éditeurs de dessin et les systèmes de
capture schématique permettent aux
utilisateurs de créer des diagrammes
complexes à partir de composants simples.
L'utilisateur peut regrouper des composants
pour former des composants plus grands, qui
à leur tour peuvent être regroupés pour
former des composants encore plus grands.
Une implémentation simple pourrait
définir des classes pour les primitives
graphiques telles que Text and Lines
ainsi que d'autres classes qui agissent
comme des conteneurs pour ces
primitives.
Mais il y a un problème avec cette approche:
■ le code qui utilise ces classes doit traiter
les objets primitifs et conteneurs
différemment, même si la plupart du
temps l'utilisateur les traite de manière
identique, avoir à distinguer ces objets
rend l'application plus complexe.
■ Le modèle composite décrit comment
utiliser la composition récursive afin que
les clients n'aient pas à faire cette
distinction.
La clé du Composite pattern est une classe
abstraite qui représente à la fois les
primitives (primitives) et leurs
conteneurs(containers).
Pour le système graphique, cette classe est
Graphic.
Graphic déclare des opérations comme
Draw spécifiques aux objets graphiques. Il
déclare également les opérations que tous
les objets composites partagent, telles que
les opérations d'accès et de gestion de ses
enfants.
■ Les sous-classes Line, Rectangle et Text
définissent des objets graphiques
primitifs.
■ Ces classes implémentent Draw pour
dessiner des lignes, des rectangles et du
texte, respectivement.
■ Étant donné que les graphiques primitifs
n'ont pas de graphiques enfants, aucune
de ces sous-classes ne met en œuvre
des opérations liées aux enfants.
■ La classe Picture définit un agrégat
d'objets Graphic.
■ Picture implémente Draw pour
appeler Draw sur ses enfants et
implémente les opérations liées aux
enfants en conséquence. Parce que
l'interface d'image est conforme à
l'interface graphique, les objets
image peuvent composer d'autres
images de manière récursive.
The following diagram shows a typical
composite object structure of recursively
composed Graphic objects:
Applicability
Utilisez le motif composite lorsque
▪ vous souhaitez représenter des hiérarchies
partielles d'objets.
▪ vous voulez que les clients puissent ignorer
la différence entre les compositions
d'objets et les objets individuels. Les clients
traiteront tous les objets de la structure
composite de manière uniforme
The Component
Structure interface describes
operations that are
common to both
simple and complex
elements of the tree.
The Leaf is a basic element of
Structure a tree that doesn’t have sub-
elements.
Usually, leaf components end
up doing most of the real
work, since they don’t have
anyone to delegate the work
to.
The Container (composite) is an element
that has sub-elements: leaves or other
Structure containers. A container doesn’t know the
concrete classes of its children. It works
with all sub-elements only via the
component interface.
Upon receiving a request, a container
delegates the work to its sub-elements,
processes intermediate results and then
returns the final result to the client.
Structure The Client works with all
elements through the
component interface.
As a result, the client can work
in the same way with both
simple or complex elements of
the tree.
Structure
Une structure d'objet composite
typique pourrait ressembler à ceci:
Participants
Component (Graphic)
▪ déclare l'interface des objets dans
la composition.
▪ implémente le comportement par
défaut pour l'interface commune à
toutes les classes, le cas échéant.
▪ déclare une interface pour accéder
et gérer ses composants enfants.
Participants
Leaf (Rectangle, Line, Text,etc.)
▪ représente des objets feuilles dans
la composition. Une feuille n'a pas
d'enfants.
▪ définit le comportement des objets
primitifs dans la composition.
Participants
Composite (Picture)
▪ définit le comportement des
composants ayant des enfants.
▪ stocke les composants enfants.
▪ implémente les opérations liées
aux enfants dans l'interface
Component.
Participants
Client
▪ définit le comportement des
composants ayant des enfants.
▪ stocke les composants enfants.
▪ implémente les opérations liées
aux enfants dans l'interface
Component.
Les clients utilisent l'interface de classe
Component pour interagir avec les objets de
la structure composite.
Si le destinataire est une feuille,
la demande est traitée
directement.
Si le destinataire est un Composite, il
transmet généralement les demandes
à ses composants enfants, effectuant
éventuellement des opérations
supplémentaires avant et/ou après le
transfert.
Consequences
The Composite pattern
▪ définit des hiérarchies de classes, comprenant
des objets primitifs et des objets composites.
▪ Les objets composites peuvent être composés
en objets plus complexes, qui à leur tour
peuvent être composés, et ainsi de suite
récursivement.
▪ Partout où le code client attend un objet primitif,
il peut également prendre un objet composite.
Consequences
The Composite pattern
▪ rend le client simple.
▪ Les clients peuvent traiter les structures
composites et les objets individuels de manière
uniforme.
▪ Les clients ne savent généralement pas (et ne
devraient pas s'en soucier) s'ils ont affaire à un
composant feuille ou composite. Cela simplifie
le code client, car il évite d'avoir à écrire des
fonctions de tag-and-case-statement-style sur
les classes qui définissent la composition.
Consequences
The Composite pattern
▪ facilite l'ajout de nouveaux types de
composants.
▪ Les sous-classes Composite ou Leaf
nouvellement définies fonctionnent
automatiquement avec les structures existantes
et le code client.
▪ Les clients ne doivent pas être modifiés pour les
nouvelles classes de composants.
▪ peut rendre votre conception trop générale
Consequences
The Composite pattern
▪ L'inconvénient de le rendre facile d'ajouter de
nouveaux composants est qu'il rend plus
difficile de limiter les composants d'un
composite.
▪ Parfois, vous souhaitez qu'un composite ne
comporte que certains composants. Avec
Composite, vous ne pouvez pas compter sur le
système pour appliquer ces contraintes pour
vous. Vous devrez plutôt utiliser des vérifications
au moment de l'exécution.
xample
Dans cet exemple, le motif composite vous permet
d'implémenter l'empilement de formes
géométriques dans un éditeur graphique.
The geometric shapes editor example.
La classe Compound Graphic est un
conteneur qui peut comprendre n'importe
quel nombre de sous-formes, y compris
d'autres formes composées.
Une forme composée a les mêmes
méthodes qu'une forme simple. Cependant,
au lieu de faire quelque chose par elle-
même, une forme composée transmet
récursivement la demande à tous ses
enfants et «résume» le résultat.
Le code client fonctionne avec toutes les
formes via l'interface unique commune à
toutes les classes de formes. Ainsi, le client
ne sait pas s'il travaille avec une forme
simple ou une forme composée. Le client
peut travailler avec des structures d'objets
très complexes sans être couplé à des
classes concrètes qui forment cette
structure.
Decorator
pattern
Attachez
dynamiquement des
responsabilités
supplémentaires à un
objet.
Intent
Attach additional responsibilities to an
object dynamically.
Decorators provide a flexible alternative
to subclassing for extending functionality
Also Known As
Wrapper
xample
The ornaments that are added to pine or fir trees
are examples of Decorators. Lights, garland, candy
canes, glass ornaments, etc., can be added to a
tree to give it a festive look. The ornaments do not
change the tree itself which is recognizable as a
Christmas tree regardless of particular ornaments
used. As an example of additional functionality,
the addition of lights allows one to "light up" a
Christmas tree.
Another example: assault gun is a deadly weapon
on it's own. But you can apply certain
"decorations" to make it more accurate, silent and
devastating.
Structure
The Component
declares the
common interface
for both wrappers
and wrapped
objects.
Structure
Concrete
Component is a
class of objects
being wrapped. It
defines the basic
behavior, which
can be altered by
decorators.
Structure The Base Decorator
class has a field for
referencing a
wrapped object. The
field’s type should be
declared as the
component interface
so it can contain both
concrete components
and decorators. The
base decorator
delegates all
operations to the
wrapped object.
Structure Concrete Decorators
define extra
behaviors that can be
added to components
dynamically. Concrete
decorators override
methods of the base
decorator and
execute their
behavior either
before or after calling
the parent method.
Structure
The Client can wrap
components in
multiple layers of
decorators, as long as
it works with all
objects via the
component interface.
xample
Ce que nous faisons maintenant, c'est prendre une
pizza et la «décorer» avec des garnitures au moment
de l'exécution:
1. Take a pizza object.
2. “Decorate” it with a Capsicum object.
3. “Decorate” it with a CheeseBurst object.
4. Call getCost() and use delegation instead of inheritance
to calculate the toppings cost.
In this example, the Decorator pattern
lets you compress and encrypt sensitive
data independently from the code that
actually uses this data.
xample
L'application encapsule l'objet source de données avec une
paire de décorateurs. Les deux wrappers modifient la façon
dont les données sont écrites et lues sur le disque:
Juste avant que les données ne soient écrites sur le
disque, les décorateurs les chiffrent et les compressent. La
classe d'origine écrit les données chiffrées et protégées dans
le fichier sans connaître la modification.
Juste après la lecture des données sur le disque, elles
passent par les mêmes décorateurs, qui les décompressent
et les décodent.
Les décorateurs et la classe de source de données
implémentent la même interface, ce qui les rend tous
interchangeables dans le code client.
Facade
pattern
Intent
Provide a unified interface to a set
of interfaces in a subsystem.
Facade defines a higher-level
interface that makes the subsystem
easier to use
Bridge
pattern
Proxy
pattern
Flyweight
pattern
Références
■ Erich Gamma, Richard Helm, Ralph Johnson, John M.
Vlissides, Design Patterns_ Elements of Reusable Object-
Oriented Software -Addison-Wesley Professional, 1994,
■ [Link]
■ [Link]
■ [Link]
.[Link]/category/design-patterns/
■ [Link]
■ [Link]