Design Patterns Matrix
Design Patterns Matrix
Not all of the Gang of Four design patterns are included because not all of them are covered in
the course. Furthermore, we use a variation on the classification of the GoF patterns:
The Decorator and Proxy patterns are classified as Structural patterns by the GoF. Since they both add
instead of just combining functionality, I believe they are more behavioral in nature. In our minds, the Bridge
can be considered as either a Structural or Behavioral pattern. As a structural pattern, it allows the use of
two different, given, implementation in the same way. As a behaviorally pattern, it helps identify that there
are variations of an implementation. We have also reclassified several Behavioral patterns as Decoupling
patterns (a new classification of ours). That is because these patterns are more about decoupling than about
managing new behavior.
This is a work in progress. Updates will be announced through our e-zine. You can subscribe
to this by sending a message to [email protected] and putting subscribe in the subject.
Contents:
Abstract Factory* Composite* Visitor
Builder Façade* Chain of Responsibility*
Factory Method* Proxy – Virtual* Iterator*
Object Pool* Decorator* Mediator*
Prototype Proxy – adding function* Memento
Singleton* State* Observer*
Adapter* Strategy* Proxy – accessibility*
Bridge* Template Method* Model-View-Controller
* Along with the Analysis Matrix, these are considered minimal competencies for software
developers by Net Objectives
Indicators in analysis: Several different kinds of complex objects can be built with the same overall build process, but where
B there is variation in the individual construction steps.
u Indicators in design: You want to hide the implementation of instantiating complex object, or you want to bring together all of the
rules for instantiating complex objects.
i
l
d
e
r
Indicators in analysis: There are different commonalities whose implementations are coordinated with each other.
F M Indicators in design: A class needs to instantiate a derivation of another class, but doesn’t know which one. Factory method
a e allows a derived class to make this decision.
c t Field notes: The Factory method is often used with frameworks. It is also used when the different implementations of one class
t h hierarchy requires a specific implementation of another class hierarchy. Note that a factory method pattern is not simply a method
that serves as a factory. The pattern specifically involves the case where the factory is varied polymorphically. Factory Method is
o o also very useful when unit testing with Mock Objects.
r d Principle manifested: Encapsulate the relationship between class hierarchies.
y
Indicators in analysis: There are rules about how to manage a set of objects. These can relate to the number, the lifespan,
O P handling error conditions, load balancing and more.
b o Indicators in design: There are rules about creating and managing your objects.
j o Field notes: The object pool is a great way to defer the management of the lifespan of your objects. Use some trivial to implement
e l rule, but encapsulate it in the object pool. Once you have the system working and you better understand the rules for object
creation and management, implement these rules in the encapsulated methods.
c
t
method to get the constructed object returned to it. Derive classes + buildStep1() u
+ buildStep2()
from the builder object to specialize steps.
builder->buildStep1()
builder->buildStep2() + getObject() i
getObject() l
Encapsulates: Rules for constructing complex objects. d
ConcreteBuilder1 ConcreteBuilder2 e
+ buildStep1() + buildStep1()
+ buildStep2() + buildStep2() r
+ getObject() + getObject()
Have a method in the abstract class that is abstract (pure virtual). Application
Document
The abstract class’s code will refer to this method when it needs to + createDocument() F M
instantiate a contained object. Note, however, that it doesn’t know
which one it needs. That is why all classes derived from this one
must be
abstract
a e
must implement this method with the appropriate new command to c t
instantiate the proper object. MyDoc MyAp t h
+ createDocument() return new MyDoc
o o
Encapsulates: How two inheritance hierarchies are related to each
other.
r d
Note: in this example createDocument is called a
factory method. Application is not a factory object.
y
Create a class (“ReusablePool”) that encapsulates all of the rules
for creating and managing the pooled objects. This class has only +client
O P
one instantiation (use Singleton to enforce this). When a new Client
1 +manager
objects.
0..* 1 t
Reusable
Indicators in analysis: There are a set of related objects using another set of objects. This second set represents an
implementation of the first set. The first set uses the second set in varying ways.
Indicators in design: There is a set of derivations that use a common set of objects to get implemented.
B Indication pattern is not being used when it should be: There is a class hierarchy that has redundancy in it. The redundancy is
r in the way these objects use another set of object. Also, if a new case is added to this hierarchy or to the classes being used, that
i will result in multiple classes being added.
d Relationships involved: The using classes (the GoF’s “Abstraction”) use the used classes (the GoF’s “Implementation”) in
g different ways but don’t want to know which implementor is present. The pattern “bridges” the what (the abstraction) to the how
(the implementation).
e Field notes: Although the implementer to use can vary from instance to instance, typically only one implementer is used for the
life of the using object. This means we usually select the implementer at construction time, either passing it into the constructor
or having the constructor decide which implementer should be used.
C Indicators in analysis: There are single things and groups of things that you want to treat the same way. The groups of things
o are made up of other groups and of single things (i.e., they are hierarchically related).
Indicators in design: Some objects are comprised of collections of other objects, yet we want to handle all of these objects in the
m same way.
p Indication pattern is not being used when it should be: The code is distinguishing between whether a single object is present
o or a collection of objects is present.
s Variation encapsulated: Whether an item is a single entity or whether it is composed of several sub-components.
Field notes: Whether or not to expose an interface that would allow the client to navigate the composite is a decision that must be
i considered. The ideal composite would hide its structure, and thus the navigation would not be supported, but specifics in the
t problem domain often do not allow this. Often, using a Data Object can eliminate the need for traversal by the client
e
Indicators in analysis: A complex system will be used which will likely not be utilized to its full extent.
Indicators in design: Reference to an existing system is made in similar ways. That is, you see combinations of calls to a system
repeated over and over again.
F Indication pattern is not being used when it should be: Many people on a team have to learn a new system although each
a person is only using a small aspect of it.
ç Field notes: Not usually used for encapsulating variation, but different facades derived from the same abstract class can
a encapsulate different sub-systems. This is called an encapsulating façade. The encapsulating facade can have many positive
side-effects, including support for demonstration/limited function versions of an application.
d Essence of Pattern: Don’t settle for complex – make it simple.
e
Indicators in analysis and design: Performance issues (speed or memory) can be foreseen because of the cost of having objects
around before they are actually used.
Indication pattern is not being used when it should be: Objects are being instantiated before they are actually used and the
P V extent of this is causing performance problems.
r i Variation encapsulated: Although each proxy contains only one new function or way of connecting to the proxy object, this
o r function can be changed (statically) in the future without affecting those objects that use the proxy.
x t Field notes: This pattern often comes up to solve scalability issues or performance issues that arise after a system is
y u working.
a
l
Define a new class (or classes) that has the required interface.
Have this new class use the existing system.
Client
Encapsulates the true nature of a sub-system. F
Facade ComplexSysA a
ç
a
provides simpler ComplexSysB d
interface
e
The Client refers to the proxy object instead of an object from the
Client Abst ract
original class. The proxy object remembers the information to proxy P V
required to instantiate the original class but defers its instantiation. + operation()
When the object from the original class is actually needed, the r i
proxy object instantiates it and then makes the necessary request to o r
it. x t
Virt ualSubject RealSubject
y u
Encapsulates the deferring of some action (e.g., instantiation, + operation() + operation()
making a connection) and the rule(s) to manage it.
- a
realsubject->operation() l
Have the class that uses the algorithm contain an abstract class that S
Client
has an abstract method specifying how to call the algorithm. Each t
derived class implements the algorithm as needed. Context Strategy
+ request(Strategy) + algorithm()
r
Encapsulates that there are multiple algorithms. a
t
e
StrategyA StrategyB g
+ algorithm() + algorithm()
y
Create an abstract class that implements a procedure using abstract AbstractTemplate T
methods. These abstract methods must be implemented in derived Client + templateMethod() e M
classes to actually perform each step of the procedure. If the steps + operation1() templateMethod:
vary independently, each step may be implemented with a strategy + operation2() ... m e
pattern.
operation1()
...
p t
operation2() l h
Encapsulates the different implementations of the method. ...
ComcreteClass a o
+ operation1()
+ operation2()
t d
e
Make an abstract class that represents the tasks to be performed. AbstractTask Client Structure
Add a method to this class for each concrete class you started with + visitElTypeA()
V
(your original entities). Add a method to the classes that you are + visitElTypeB()
M Indicators in analysis and design: Many objects need to communicate with many other objects yet this communication cannot
e be handled with the observer pattern.
Indication pattern is not being used when it should be: The system is tightly coupled due to inter-object communication
d requirements.
i Field notes: When several objects are highly coupled in the way they interact, yet this set of rules can be encapsulated in one
a place. Mediator can be useful in decoupling tool-generated code (GUI's and database connections, for example) from hand-
t crafted code, and can also help in making dependent objects more testable.
o
r
Indicators in analysis and design: The state of an object needs to be remembered so we can go back to it (e.g., undo an
M action).
Indication pattern is not being used when it should be: The internal state of an object is exposed to another object. Or,
e copies of an object are being made to remember the object’s state, yet this object contains much information that is not state
m dependent. This means the object is larger than it needs to be or contains an open connection that doesn’t need to be
e remembered.
n Field notes: This pattern is useful when making copies of the object whose state is being remembered would be inefficient. It's
also commonly used to create "multiple undo levels". The use of inner classes can help to make Mementos robust, since it
t prevents a memento generated by one instance being applied accidentally to another.
o
O Indicators in analysis and design: Different things (objects) that need to know when an event has occurred. This list of
b objects may vary from time to time or from case to case.
Indication pattern is not being used when it should be: When a new object needs to be notified of an event occurring the
s programmer has to change the object that detects the event.
e Variation encapsulated: The list of objects that need to know about an event occurring.
r Field notes: This pattern is used extensively in the JFC for event handling and is supported with the Observable class and
v Observer interface. Also note that C# multicast delegates are essentially implementations of the Observer pattern.
Essence of pattern: 1) there is a changing list of observers, 2) all observers have the same interface, 3) it is the observers
e responsibility to register it the event they are ‘observing’
r
P c Indicators in analysis and design: Are any of the things we work with remote (i.e., on other machines)? An existing object
r e needs to use an object on another machine and doesn’t want to have to worry about making the connection (or even know about
o s the remote connection).
x i Indication pattern is not being used when it should be: The use of an object and the set-up of the connection to the object are
y b found together in more than one place.
| i Variation encapsulated: Although each proxy contains only one new function or way of connecting to the proxy object, this
l function can be changed (statically) in the future without affecting those objects that use the proxy.
A i Field notes: The Proxy is a useful pattern to use when it is possible a remote connection will be needed in the future. In this
c t case, only the Proxy object need be changed - not the object actually being used.
- y
The Proxy pattern has a new object (the Proxy) stand in place of another, P c
Client Abstract
already existing object (the Real Subject). The proxy encapsulates any to proxy r e
+ operation()
rules required for access to the real subject. The proxy object and the real o s
subject object must have the same interface so that the Client does not x i
need to know a proxy is being used. Requests made by the Client to the y b
proxy are passed through to the Real Subject with the proxy doing any Proxy_Remote RealSubject | i
necessary processing to make the remote connection. + operation() + operation() l
A i
Encapsulates how to access an object. realsubject->operation() c t
- y
Mo del
View ConcreteObservers
- CoreData
- SetOfObservers - my Model
- my Cont roller
+ attach(Observer) get
attac
data
h
+ detach(Observer) + initializ e(Model)
+ notify() + makeController()
+ getData() + ac tivate()
+ display() display Controller
+ update ()
- myModel
- myView
service
+ initialize(Model, View)
there is no concrete subject in attach + handleEvent()
this exam ple + update()
The Model-View-Controller (MVC) is primarily used when building GUIs. However, it can be used
anytime you have an interactive type system. It is used to de-couple your data, your presentation of the
data and the logic for handling the events from each other.
The Use the Analysis matrix to collect variation between the different cases you have to deal with. Do not try
Analysis to make designs from it while you are collecting it. However, the consistencies and inconsistencies
Matrix between the cases will give you clues. Remember, we will implement the rows as Strategies, Proxies,
Decorators, Bridges, etc. We will implement the columns with the Abstract Factory.
Case 1 Case 2 Case 3 Case 4
one thing that These are the concrete implementations for the ways to whatever is
is varying varying that is listed on the left.
another thing These are the concrete implementations for the ways to whatever is
that varies varying that is listed on the left.
still another These are the concrete implementations for the ways to whatever is
thing that varying that is listed on the left.
varies
… …
varies
still another thing
These imple-
These imple-
These imple-
These imple-
that varies
…
Are you concerned with interfaces, changing, simplifying or handling disparate type objects in the same way?
Adapter – do we have the right stuff but the wrong interface? (Used to fit classes into patterns as well)
Composite – do we have units and groups and want to treat them the same way?
Façade – do we want to simplify, beautify, or OO-ify an existing class or syb-system?
Observer – do various entities need to know about events that have occurred?
Chain of Responsibility – do we have different objects that can do the job but we don’t want the client object know
which is actually going to do it?
Iterator – do we want to separate the collection from the client that is using it so we don’t have to worry
about having the right collection implementation?
Mediator – do we have a lot of coupling in who must talk to who?
State – do we have a system with lots of states where keeping track of code for the different states is difficult?
Remember the relationship between commonality/variability analysis, the conceptual, specification, implementation
perspectives and how these are implemented in object-oriented languages.
by looking at what
Commonality Conceptual Abstract
these objects must do
analysis perspective class
(conceptual perspective)
Operations we determine how to
call them (specification
perspective)
Specification
perspective Concrete Concrete
class class
Operations Operations
Variability Implementation
When implementing these classes, ensure that
analysis perspective
the API provides sufficient information to
enable proper implementation and decoupling
?
Client Pre-Existing
which pattern?
Quality Training
Design Patterns Effective ASP.NET Use Cases On-Site Courses!
Lean Software Development
ScrumMaster Certification by Net Objectives Instructor Led / Web-
Based Training for
Test-Driven Development Languages
Extreme Programming, Effective Programming, RUP
_______________________________________________________________________________________________________________________________________________________________________________________________________________
"If I were tasked with bringing in an “Two things in life are certain: death and taxes” – Ben Franklin
outside design course, Net
Objectives’ would be on the top of my “In the information age, three things in life are certain – death,
list" - John Terrell, Microsoft taxes, and requirements will change” – Alan Shalloway
Lean Software Development and ScrumMaster Certification by Net Objectives
We offer training in both Lean Software Development and in Scrum. Our Lean Software Development training is based on Mary and Tom
Poppendieck’s work. Our Scrum training includes certification in being a ScrumMaster. We also provide training in how to be a Product
Champion (playing the role of the customer) in an agile project.
Agile Development Best Practices
In simple terms, an Agile Project is one that is predicated on making sure it is always doing the right thing, not merely following a plan that
has since gone out of date. The cornerstone of this approach is getting and adapting to feedback as the project progresses. Most projects
can't do this, so they fall further behind and either fail or provide inferior products. Changes are of many types, but the most common (and
important) changes are to the system's requirements. This course analyzes what it means to be an agile project, and provides a number of
best practices that provide and/or enhance agility. Different agile practices (including RUP, XP and Scrum) are discussed.
Agile Use Case Analysis
This 3-day course provides theory and practice in writing use cases, an understanding of how use cases fit into software development, and
the use of the “ever unfolding story” to incrementally refine the use cases into a robust requirements model. The course is largely based on
Alistair Cockburn's book "Writing Effective Use Cases" - winner of the Jolt Productivity Award for 2001. As a certified member of
Cockburn and Associates, we are one of the few companies authorized to teach it.
Design Patterns Explained: A New Perspective on Object-Oriented Design
This course goes beyond merely teaching several design patterns. It also teaches the principles and strategies that make design patterns
good designs. This enables students to use these advanced design techniques in their problems whether design patterns are even present.
After teaching several patterns and the principles underneath them, the course goes further by showing how patterns can work together to
create robust, flexible, maintainable designs.
Test-Driven Development
The practice of Agile Software Development requires, among other things, a high degree of flexibility in the coding process. As we get
feedback from clients, stakeholders, and end users, we want to be able to evolve our design and functionality to meet their needs and
expectations. This implies an incremental process, with frequent (almost constant) change to the code we're working on. Refactoring, the
discipline of changing code without harming it, is an essential technique to enable this process. Unit testing, which ensures that a given
change has not caused an unforeseen ripple effect in the system, is another.