But how to get to the design objects and mechanisms? ... “Design Patterns:
Elements of Reusable Object-. Oriented Software,” Gamma, Helm, Johnson,.
SE464/CS446/ECE452
Object-Oriented Design Patterns Part I Instructor: Krzysztof Czarnecki
1
• These slides are mainly based on: – Tutorial slides by John Vlissides, see http://www.research.ibm.com/designpatterns/pubs/dptutorial.pdf • Text © 1994-1999 by Erich Gamma, Richard Helm, Ralph Johnson, John Vlissides • Diagrams © 1995 by Addison-Wesley Publishing Company • Note: Compared to the original tutorial by John Vlissides, the diagram notation have been upgraded from OMT to UML and some text has been updated
– Some material by Ian Davis and Grant Weddell and P. Dasiewicz 2
Overview ÎMotivation and Concept – Observer
• Example: WYSIWYG Editor – – – –
Composite Strategy Decorator Abstract Factory 3
Analysis vs. Design • Analysis – Domain level - modeling “real world” objects – Many domain objects will not make into the design – Domain structures usually make poor design structures
• Design – Assigning responsibilities to object – Taking “illities” (maintainability, reusability, etc.) and portability into account – Devising mechanisms – But how to get to the design objects and mechanisms? 4
Motivation and Concept • OOD methods emphasize design notations © E. Gamma, R. Helm, R. Johnson, J. Vlissides and Addison-Wesley
– Fine for specification, documentation
• But OOD is more than just drawing diagrams – Good draftsmen ≠ good designers
• Good OO designers rely on lots of experience – At least as important as syntax
• Most powerful reuse is design reuse – Match problem to design experience 5
Motivation and Concept
© E. Gamma, R. Helm, R. Johnson, J. Vlissides and Addison-Wesley
• OO systems exploit recurring design structures that promote – – – –
Abstraction Flexibility Modularity Elegance
• Therein lies valuable design knowledge • Problem: capturing, communicating, and applying this knowledge 6
What Is a Design Pattern?
© E. Gamma, R. Helm, R. Johnson, J. Vlissides and Addison-Wesley
• A design pattern – Is a common solution to a recurring problem in design – Abstracts a recurring design structure – Comprises class and/or object • • • •
Dependencies Structures Interactions Conventions
– Names & specifies the design structure explicitly – Distils design experience 7
What Is a Design Pattern?
© E. Gamma, R. Helm, R. Johnson, J. Vlissides and Addison-Wesley
• A design pattern has 4 basic parts: – – – –
• • • •
1. Name 2. Problem 3. Solution 4. Consequences and trade-offs of application
Language- and implementation-independent A “micro-architecture” Adjunct to existing methodologies (Unified, OMT, etc.) No mechanical application – The solution needs to be translated into concrete terms in the application context by the developer 8
© E. Gamma, R. Helm, R. Johnson, J. Vlissides and Addison-Wesley
Example: Observer
9
Goals
© E. Gamma, R. Helm, R. Johnson, J. Vlissides and Addison-Wesley
• Codify good design – Distil and disseminate experience – Aid to novices and experts alike – Abstract how to think about design
• Give design structures explicit names – Common vocabulary – Reduced complexity – Greater expressiveness
• Capture and preserve design information – Articulate design decisions succinctly – Improve documentation
• Facilitate restructuring/refactoring – Patterns are interrelated – Additional flexibility
10
Design Pattern Catalogues • GoF (“the gang of four”) catalogue – “Design Patterns: Elements of Reusable ObjectOriented Software,” Gamma, Helm, Johnson, Vlissides, Addison-Wesley, 1995
• POSA catalogue – Pattern-Oriented Software Architecture, Buschmann, et al.; Wiley, 1996
• … 11
© E. Gamma, R. Helm, R. Johnson, J. Vlissides and Addison-Wesley
Classification of GoF Design Pattern Creational
Structural
Behavioral
Factory Method Abstract Factory Builder Prototype Singleton
Adapter Bridge Composite Decorator Flyweight Facade Proxy
Interpreter Template Method Chain of Responsibility Command Iterator Mediator Memento Observer State Strategy Visitor
12
Design Pattern Template (First Half ) • •
Name (and classification) Intent
© E. Gamma, R. Helm, R. Johnson, J. Vlissides and Addison-Wesley
– Short description of pattern and its purpose
•
Also known as – Other names that people have for the pattern
•
Motivation – Motivating scenario demonstrating pattern's use
•
Applicability – Circumstances in which pattern applies
•
Structure – Graphical representation of the pattern – GoF used OMT and interaction diagrams (a precursor to UML)
•
Participants – Participating classes and/or objects and their responsibilities
•
...
13
Design Pattern Template (Second Half ) • •
... Collaborations
© E. Gamma, R. Helm, R. Johnson, J. Vlissides and Addison-Wesley
– How participants cooperate to carry out their responsibilities
•
Consequences – The results of application, benefits, liabilities
•
Implementation – Implementation pitfalls, hints, or techniques, plus any language-dependent issues
•
Sample code – Sample implementations in C++, Java, C#, Smalltalk, etc.
•
Known uses – Examples drawn from existing systems
•
Related patterns – Discussion of other patterns that relate to this one
14
Observer (Behavioral)
© E. Gamma, R. Helm, R. Johnson, J. Vlissides and Addison-Wesley
• Intent – Define a one-to-many dependency between objects so that when one object changes state, all its dependents are notified and updated automatically
• Applicability – When an abstraction has two aspects, one dependent on the other – When a change to one object requires changing others, and you don't know how many objects need to be changed – When an object should notify other objects without making assumptions about who these objects are
15
Observer (Cont'd) • Structure Subject © E. Gamma, R. Helm, R. Johnson, J. Vlissides and Addison-Wesley
-observers +attach(in o : Observer) +detach(in o : Observer) +notify()
1
*
Observer +update()
{for all o in observers { o.update() } }
ConcreteSubject
-subject
ConcreteObserver
-subjectState +getState()
-observerState 1
{return subjectState
*
}
+update()
{observerState = subject.getState()
}
16
Observer - Example • Consider ClockTimer a concrete subject that stores and maintains the time of day. It notifies its observers each second and provides the interface to retrieve time units: class ClockTimer : public Subject { public: ClockTimer(); virtual int GetHour(); virtual int GetMinute(); virtual int GetSecond(); void Tick(); };
void ClockTimer::Tick () { // update internal time-keeping state // ... Notify(); }
the Tick operation is called by some timer and it updates the ClockTimer’s internal state and calls Notify to inform observers.
17
• consider a DigitialClock concrete Observer: class DigitalClock: public Widget, public Observer { public: DigitalClock(ClockTimer*); virtual ~DigitalClock(); virtual void Update(Subject*); // overrides Observer operation virtual void Draw(); // overrides Widget operation; // defines how to draw the digital clock private: DigitalClock::DigitalClock (ClockTimer* s) { ClockTimer* _subject; _subject = s; };
_subject->Attach(this); } DigitalClock:: ~ DigitalClock () { _subject->Detach(this); }
18
• before drawing the clock face, the UpDate function checks if the notifying subject is the clock’s subject: void DigitalClock::Update (Subject* theChangedSubject) { if (theChangedSubject == _subject) { Draw(); } } void DigitalClock::Draw () { // get the new values from the subject int hour = _subject->GetHour(); int minute = _subject->GetMinute(); // etc. // draw the digital clock }
19
• as well, an AnalogClock class can be defined as: class AnalogClock : public Widget, public Observer { public: AnalogClock(ClockTimer*); virtual void Update(Subject*); virtual void Draw(); // ... }; 20
• can also create an AnalogClock and a DigitalClock that show the same time: ClockTimer* timer = new ClockTimer; AnalogClock* analogClock = new AnalogClock(timer); DigitalClock* digitalClock = new DigitalClock(timer);
• on each clock tick, both clocks will be updated and will redisplay themselves
21
Observer (Cont'd)
© E. Gamma, R. Helm, R. Johnson, J. Vlissides and Addison-Wesley
• Consequences + Modularity: subject and observers may vary independently + Extensibility: can define and add any number of observers + Customizability: different observers provide different views of subject – Unexpected updates: observers don't know about each other – Update overhead: might need hints
• Implementation – Subject-observer mapping – Dangling references – Avoiding observer-specific update protocols: the push and pull models – Registering modifications of interest explicitly 22
Observer (Cont'd)
© E. Gamma, R. Helm, R. Johnson, J. Vlissides and Addison-Wesley
• Known uses – Smalltalk model-view-controller (MVC) – Interviews (subjects and views) – Andrew (data objects and views)
• Benefits – – – –
Design reuse Uniform design vocabulary Enhance understanding, restructuring Basis for automation 23
Overview • Motivation and Concept – Observer
ÎExample: WYSIWYG Editor – – – –
Composite Strategy Decorator Abstract Factory 24
Example: WYSIWYG Editor
© E. Gamma, R. Helm, R. Johnson, J. Vlissides and Addison-Wesley
• 7 design problems: – – – – –
Document structure Formatting Embellishment Multiple look & feels Multiple window systems – User operations – Spelling checking & hyphenation 25
Overview • Motivation and Concept – Observer
• Example: WYSIWYG Editor ÎComposite - Document Structure – Strategy - Formatting – Decorator - Embellishment – Abstract Factory - Multiple Look&Feels 26
Document Structure
© E. Gamma, R. Helm, R. Johnson, J. Vlissides and Addison-Wesley
• Goals: – Present document's visual aspects – Drawing, hit detection, alignment – Support physical structure (e.g., lines, columns)
• Constraints: – Treat text and graphics uniformly – No distinction between one and many 27
© E. Gamma, R. Helm, R. Johnson, J. Vlissides and Addison-Wesley
Document Structure (Cont'd) • Solution: Recursive composition
28
© E. Gamma, R. Helm, R. Johnson, J. Vlissides and Addison-Wesley
Document Structure (Cont'd)
• Object structure
29
Document Structure (Cont'd)
© E. Gamma, R. Helm, R. Johnson, J. Vlissides and Addison-Wesley
• Glyph: base class for composable graphical objects • Basic interface: Task
Operations
appearance
void draw(Window)
hit detection
boolean intersects(Coord, Coord)
structure
insert(Glyph) void remove(Glyph) Glyph child(int) Glyph parent()
• Subclasses: Character, Image, Space, Row, Column 30
Document Structure (cont'd) Glyph
© E. Gamma, R. Helm, R. Johnson, J. Vlissides and Addison-Wesley
-children
Row 1
*
+draw(in w : Windows) +intersects(in c1 : Coord, in c2 : Coord) +insert(in g : Glyph, in i : int) +...()
Character
Rectangle
Polygon
-lb : Coord -rt : Coord +draw() +intersects()
-v[*] : Coord
-c : char +draw(in ...) +intersects(in ...) +insert(in ...)
*
+draw() +intersects()
-children
+draw() +intersects()
Column +draw(in ...) +intersects(in ...) +inserts(in ...)
31
1
Composite (Structural)
© E. Gamma, R. Helm, R. Johnson, J. Vlissides and Addison-Wesley
• Intent – Treat individual objects and multiple, recursively-composed objects uniformly
• Applicability – Objects must be composed recursively, – And there should be no distinction between individual and composed elements, – And objects in the structure can be treated uniformly 32
Composite (Cont'd) Component
© E. Gamma, R. Helm, R. Johnson, J. Vlissides and Addison-Wesley
• Structure
* +operation() +add(in c : Component) +remove(in c : Component) +getChild(in i : int)
Leaf +operation()
-children
Composite +operation() +add(in c : Composite) +remove(in c : Composite) +getChild(in i : int)
1
{ forall g in children g.operation(); }
33
Composite (Cont'd)
© E. Gamma, R. Helm, R. Johnson, J. Vlissides and Addison-Wesley
• Consequences + Uniformity: treat components the same regardless of complexity + Extensibility: new Component subclasses work wherever old ones do – Overhead: might need prohibitive numbers of objects
• Implementation – Do Components know their parents? – Uniform interface for both leaves and composites? – Don't allocate storage for children in Component base class 34 – Responsibility for deleting children
Composite (Cont'd)
© E. Gamma, R. Helm, R. Johnson, J. Vlissides and Addison-Wesley
• Known Uses – ET++ VObjects – InterViews Glyphs, Styles – Unidraw Components, MacroCommands
35
© E. Gamma, R. Helm, R. Johnson, J. Vlissides and Addison-Wesley
Question?
• What does the pattern let you vary?
36
Overview • Motivation and Concept – Observer
• Example: WYSIWYG Editor – Composite - Document Structure ÎStrategy - Formatting – Decorator - Embellishment – Abstract Factory - Multiple Look&Feels 37
Formatting • Goals: © E. Gamma, R. Helm, R. Johnson, J. Vlissides and Addison-Wesley
– Automatic linebreaking, justification
• Constraints: – Support multiple linebreaking algorithms – Don't mix up with document structure
38
Formatting (Cont'd)
© E. Gamma, R. Helm, R. Johnson, J. Vlissides and Addison-Wesley
• Solution: encapsulate linebreaking strategy • Compositor – Base class abstracts linebreaking algorithm – Subclasses for specialized algorithms, e.G., SimpleCompositor, TeXCompositor
• Composition – Composite glyph – Supplied a compositor and leaf glyphs – Creates row-column structure as directed by compositor 39
© E. Gamma, R. Helm, R. Johnson, J. Vlissides and Addison-Wesley
Formatting (Cont'd)
40
Strategy (Behavioral)
© E. Gamma, R. Helm, R. Johnson, J. Vlissides and Addison-Wesley
• Intent – Define a family of algorithms, encapsulate each one, and make them interchangeable to let clients and algorithms vary independently
• Applicability – When an object should be configurable with one of several algorithms, and all algorithms can be encapsulated, and one interface covers all encapsulations 41
Strategy (Cont'd)
© E. Gamma, R. Helm, R. Johnson, J. Vlissides and Addison-Wesley
• Structure Context (Composition) +contextInterface()
Strategy (Compositor) 1
ConcreteStrategyA +algorithmInterface()
1
+algorithmInterface()
ConcreteStrategyB +algorithmInterface()
ConcreteStrategyC +algorithmInterface()
42
Strategy (Cont'd)
© E. Gamma, R. Helm, R. Johnson, J. Vlissides and Addison-Wesley
• Consequences + + – –
Greater flexibility, reuse Can change algorithms dynamically Strategy creation & communication overhead Inflexible strategy interface
• Implementation – Exchanging information between a strategy and its context – Static strategy selection via templates
• Known uses – Interviews text formatting – RTL register allocation & scheduling strategies – Et++SwapsManager calculation engines 43
Overview • Motivation and Concept – Observer
• Example: WYSIWYG Editor – Composite - Document Structure – Strategy - Formatting ÎDecorator - Embellishment – Abstract Factory - Multiple Look&Feels 44
Embellishment
© E. Gamma, R. Helm, R. Johnson, J. Vlissides and Addison-Wesley
• Goals: – Add a frame around text composition – Add scrolling capability
• Constraints: – Embellishments should be reusable without subclassing – Should go unnoticed by clients 45
Embellishment (Cont'd)
© E. Gamma, R. Helm, R. Johnson, J. Vlissides and Addison-Wesley
• Solution: “Transparent” enclosure • MonoGlyph – Base class for glyphs having one child – Operations on MonoGlyph pass through to child
• MonoGlyph subclasses: – Frame: adds a border of specified width – Scroller: scrolls/clips child, adds scrollbars 46
Embellishment (Cont'd) • Structure © E. Gamma, R. Helm, R. Johnson, J. Vlissides and Addison-Wesley
-component
1
1 { component.draw(w); }
{ super.draw(w); drawFrame(w); }
Glyph +draw(in w : Window)
MonoGlyph
Character
Row
+draw(in w : Window)
+draw(in w : Window)
+draw(in w : Window)
Frame
Scroller
+draw(in w : Window)
+draw(in w : Window)
47
Embellishment (Cont'd) f1 : Frame
• New object structure
-component
© E. Gamma, R. Helm, R. Johnson, J. Vlissides and Addison-Wesley
s1 : Scroller
-component -strategy c1 : Composition
c2 : Compositor
-component c3 : Column
-component
-component
r2 : Row
r1 : Row
-component c4 : Character
-component
b1 : Bitmap
-component
c4 : Character
48
Decorator (Structural) • Intent © E. Gamma, R. Helm, R. Johnson, J. Vlissides and Addison-Wesley
– Augment objects with new responsibilities
• Applicability – When extension by subclassing is impractical – For responsibilities that can be withdrawn
49
Decorator (Cont'd)
© E. Gamma, R. Helm, R. Johnson, J. Vlissides and Addison-Wesley
• Structure Component (Glyph)
1
+operation()
-component
ConcreteComponent
Decorator (MonoGlyph) { component-> component.operation(); }
+operation()
+operation()
ConcreteDecoratorA
1
ConcreteDecoratorB { super.operation(); addedBehavior(); }
-addedState +operation()
+operation() +addedBehavior()
50
Decorator (Cont'd)
© E. Gamma, R. Helm, R. Johnson, J. Vlissides and Addison-Wesley
• Consequences + + + – –
Responsibilities can be added/removed at run-time Avoids subclass explosion Recursive nesting allows multiple responsibilities Interface occlusion Identity crisis
• Implementation – Interface conformance – Use a lightweight, abstract base class for Decorator – Heavyweight base classes make Strategy more attractive
51
Decorator (Cont'd)
© E. Gamma, R. Helm, R. Johnson, J. Vlissides and Addison-Wesley
• Known Uses – Embellishment objects from most OO-GUI toolkits – ParcPlace PassivityWrapper – InterViews DebuggingGlyph
52
Overview • Motivation and Concept – Observer
• Example: WYSIWYG Editor – Composite - Document Structure – Strategy - Formatting – Decorator - Embellishment ÎAbstract Factory - Multiple Look&Feels 53
Multiple Look & Feels
© E. Gamma, R. Helm, R. Johnson, J. Vlissides and Addison-Wesley
• Goals: – Support multiple look and feel standards – Generic, Motif, PM, Macintosh, Windows, ... – Extensible for future standards
• Constraints: – Don't recode existing widgets or clients – Switch look and feel without recompiling 54
Multiple Look & Feels (Cont'd)
© E. Gamma, R. Helm, R. Johnson, J. Vlissides and Addison-Wesley
Solution: Abstract the process of creating objects Instead of Scrollbar sb = new MotifScrollbar();
use Scrollbar sb = factory.createScrollbar();
where factory is an instance of MotifFactory
55
Multiple Look & Feels (Cont'd)
© E. Gamma, R. Helm, R. Johnson, J. Vlissides and Addison-Wesley
• Factory interface – Defines “manufacturing interface” – Subclasses produce specific products – Subclass instance chosen at run-time interface Factory { Scrollbar createScrollbar(); Menu createMenu(); ... } 56
Multiple Look & Feels (Cont'd) • Structure © E. Gamma, R. Helm, R. Johnson, J. Vlissides and Addison-Wesley
Factory
Glyph
+createScrollbar() +createMenu()
+draw(in w : Window)
Scrollbar PMFactory
MotifFactory
+createScrollbar() +createMenu()
+createScrollbar() +createMenu()
+draw(in w : Window)
PMScrollbar
MotifSclorrbar
+draw(in w : Window)
+draw(in w : Window)
{ return new PMScrollbar(); }
«instantiate» { return new MotifScrollbar(); }
«instantiate»
57
Abstract Factory (Creational)
© E. Gamma, R. Helm, R. Johnson, J. Vlissides and Addison-Wesley
• Intent – Create families of related objects without specifying class names
• Applicability – When clients cannot anticipate groups of classes to instantiate
58
Abstract Factory (Cont'd) •
Structure
AbstractFactory
© E. Gamma, R. Helm, R. Johnson, J. Vlissides and Addison-Wesley
+createProductA() +createProductB()
Client *
AbstractProductA
*
*
* *
ProductA1
ProductA2
«instantiate» ConcreteFactory1
ConcreteFactory2
+createProductA() +createProductB()
+createProductA() +createProductB()
«instantiate»
«instantiate»
AbstractProductB
*
«instantiate» ProductB1
ProductB2
59
Abstract Factory (Cont'd) • Participants – Abstract Factory • Declares an interface for operations that create abstract product objects
– Concrete Factory • Implements the operations to create concrete product objects
60
Abstract Factory (Cont'd) • Participants (cont’d) – Abstract Product • Declares an interface for a type of product object.
– Concrete Product • Defines a product object to be declared by the corresponding concrete factory (Implements the Abstract Product interface)
– Client • Uses only interfaces declared by Abstract Factory and Abstract Product classes
61
Abstract Factory (Cont'd) • Consequences © E. Gamma, R. Helm, R. Johnson, J. Vlissides and Addison-Wesley
+ Flexibility: removes type dependencies from clients + Allows entire suites of classes to optionally be interchanged easily at run time + Classes employed within software may not be known until runtime; e.g., OLE pictures may be inserted into documents + May wish to identify classes by GUID’s, and to register them
+ Abstraction: hides product's composition – Hard to extend factory interface to create new products
62
Abstract Factory (Cont'd) • Implementation – Parameterization as a way of controlling interface size – Configuration with Prototypes
• Known Uses – InterViews Kits – ET++ WindowSystem – Factory as test fixture 63
Overview • Motivation and Concept – Observer
• Example: WYSIWYG Editor – – – –
Composite - Document Structure Strategy - Formatting Decorator - Embellishment Abstract Factory - Multiple Look&Feels 64