Page 1
!
MI AM!Half(day!Tutorial!
11/11/2013!8:30!AM!
!
!
!
!
!
"Design Patterns Explained: From Analysis through
Implementation" !
!
!
Presented by:
Ken Pugh
Net Objectives !
!
!
!
!
!
Brought(to(you(by:(!
!
!
340!Corporate!Way,!Suite!300,!Orange!Park,!FL!32073!
888(268(8770!H!904(278([email protected] !H!www.sqe.com
Page 2
!!!!Ken!Pugh!!!Net!Objectives!!
A fellow consultant with Net Objectives, Ken Pugh helps companies transform into lean-agile organizations through training and coaching. His special interests are in communication (particularly effectively communicating requirements), delivering business value, and using lean principles to deliver high quality quickly. Ken trains, mentors, and testifies on technology topics from object-oriented design to Linux/Unix. He has written several programming books, including the 2006 Jolt Award winner Prefactoring and his latest Lean-Agile Acceptance Test Driven Development: Better Software Through Collaboration. Ken has helped clients from London to Boston to Sydney to Beijing to Hyderabad. He enjoys snowboarding, windsurfing, biking, and hiking the Appalachian Trail. Reach Ken at [email protected] !
Page 3
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
info@netobjec+ves.com000www.netobjec+ves.com0
1# #Copyright#©#2008#Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Pa*ern'Oriented'Design''
(Design'Pa*erns'Explained)'
A#New#Perspec8ve#on#ObjectDOriented#Design#
POD#Half#Day#October#2012##
2# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Teams#
! Great#designs#are#a#collabora8ve#effort#! You#will#be#part#of#a#team#for#a#couple#exercises#! Agile#teams#are#selfDorganizing##
! Form#yourself#into#three#to#five#person#teams#
Page 4
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
3# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Introduc8ons#
! Name#! What#do#you#do?#! Who#do#you#do#it#for?#
! Languages#used?##! Years#programming?#! What#paWerns#have#you#used?##
! Why#are#you#here?#! What#do#you#want#out#of#the#course?#
4# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Ken#Pugh#
ken.pugh#@netobjec8ves.com#
Photo#Size:####Height:#2.25#Posi8on:####from#top#le_#corner###Horizontal#0.75####Ver8cal#1.#Picture##Style:#Simple#Black#####Frame##
No0code0goes0in0+ll0the0test0goes0on.0A0journey0of0two0thousand0miles0begins0with0a0single0step.0
! Fellow#Consultant#! OOA&D,#Design#PaWerns,#Lean,#Scrum,#TestDDriven#
Development#
! Over#2/5#century#of#so_ware#development#experience#
! Author#of#seven#books,#including:#– 0Prefactoring:0Extreme0Abstrac+on,0Extreme0
Separa+on,0Extreme0Readability00(2006#Jolt#Award)#
– 0Interface0Oriented0Design0
– Lean0Agile0Acceptance0TestIDriven0Development:0BeKer0SoLware0Through0Collabora+on0
Page 5
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
5# #Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Lean Enterprise
Business
Management Team
ASSESSMENTS"CONSULTING"TRAINING"COACHING"
Lean for Executives Product Portfolio Management Business Product Owner
Lean Management Project Management
ILAFYT Kanban / Scrum ATDD / TDD / Design Patterns
technical process
6# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
"PaWernDOriented#Development"#
Pa*ern5oriented'development'is'matching''
'the'forces'in'the'problem'''to'the'forces'in'pa*erns'
Page 6
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
7# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Purpose#of#this#Course#
! Present#a#powerful#way#of#analyzing#and#designing#so_ware#! Incorporates:#
– Quali8es,#Principles,#and#Prac8ces##– Design#PaWerns#(seen#in#a#different#way)##
! Mostly#about#design,#not#implementa8on#! AWempts#to#change#our#paradigm#of#design#
8# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
The#Gang#of#Four#
! Design#PaWerns##– Gamma,#Helms,#Johnson,#Vlissides#
– Known#as#the#Gang#of#Four#(GOF)##! Based#on#“Timeless#Way#of#Building”#
– Christopher#Alexander##
Page 7
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
9# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Logis8cs#
! Please#phones#and#pagers#off#(or#to#vibrate)#! Break#halfway##
10# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Learning#Styles#
! People#have#different#learning#styles#– One#is#not#beWer#than#another#– MisDmatches#cause#communica8on#problems#
– Please#ask#ques8ons#if#examples#are#not#detailed#enough#
~2
See:#hWp://www.netobjec8ves.com/resources/teamDissues/#for#more#informa8on#
Page 8
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
11# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Outline#
! Beginnings##! Code#Quali8es##! The#PaWerns#
#
12# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Agenda:#PaWerns#Covered#
! Strategy#! Template#Method#
! Bridge#! Adapter#! Façade#! Abstract#Factory##
Page 9
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
13# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
The#Pyramid##
Paradigm00
PaKerns0
Wisdom0
Principles0 Prac+ces0
Quali+es##
14# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
UML#Summary#
A
B
A
B
A
B
A
B
Aggregation
A aggregates B B is a member of A
A is composed of B A contains B type objects
B implements A A depends upon B A uses B
Composition
Interface Implementation Dependency
Different#ways#to#represent#classes.
Different#rela8onships#between#classes.##Don’t#worry#about#represen8ng#the#difference#between#aggrega8on#and#composi8on.#
From#Design#PaWerns#Explained:#A#New#Perspec8ve#on##ObjectDOriented#Design.#Shalloway#and#TroW#
A
B
B is derived from A A generalizes B
Inheritance
Page 10
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
15# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Sequence#Diagram#Summary##
16# ### #16#October#2013#
Beginnings'
Page 11
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
17# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Retrospec8on#
! To#improve,##we#need#to#reflect#– What#worked#
– What#did#not#work#
! How#can#a#design#accommodate#change?#– Not#an+cipate#change#
18# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Creeping#Changes##
function() { Do_this; Do_that; Do_something_else; }
Page 12
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
19# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Creeping#Changes#(2)##
function(a) { if (a) {
Do_another_thing: //… }
else { Do_this; Do_that; Do_something_else; }
}
20# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Creeping#Changes#(3)##
function(a, b) { if (a) {
if (b) { Do_another_thing:; //… }
else { Do_one_more_thing; //.. }
} else {
Do_this; Do_that; Do_something_else; }
}
Page 13
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
21# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Spreadsheet#Conundrum#
2000#rows#10000#columns#32#MB#Flash#Drive##Access#by#individual#byte:##rowNumber#*##sizeofRow#+######columnNumber##Or##columnNumber#*#sizeofColumn##+#####rowNumber##How#will#you#store#it?###By#row?###By#column?#
22# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
How#to#organize#?#
Language / Word
ENGLISH GERMAN
NAME Name Namen
CITY City Stadt
POSTAL_CODE Zip PC
Page 14
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
23# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Implementa8on#(1)#
String getLabelForNAME(Language l ) { if (l == ENGLISH) return “Name”; else if (l == GERMAN) return “Namen”; else throw Exception(“No translation for language” + l); } // Same for the other words
24# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Implementa8on#(2)#
String getLabelForGERMAN(Word w) { if (w == NAME) return “Name”; else if (w == CITY) return “Stadt”; else if (w == POSTAL_CODE) return “PC”; else throw Exception(“No German translation for word ” + w); } // Same for the other languages
Page 15
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
25# ### #16#October#2013#
Code'QualiAes'
c#
Paradigm00PaKerns0
Wisdom0Principles0 Prac+ces0
Quali+es##
26# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Predictability#
! Cannot#predict#how#requirements#will#change#! How##to#increase#predic8ve#abili8es?#
– High#quality#code#easier#to#change#
Page 16
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
27# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Discussion#Exercise#
! Imagine#someone#brings#you#code#to#evaluate#
! What#do#you#look##for#to#decide#if#it#is#easy#to#change?##
! What#recommenda8ons#would#you#make?#
28# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Quali8es#
! In#PaWernDOriented#Development#– Focus#is#on:#
Cohesion#Coupling#NonDRedundancy#Encapsula8on#And,#overall,#Testability0
Page 17
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
29# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Cohesion#
! Cohesion##– “How#closely#opera8ons#in#a#rou8ne#[or#class]#are#related.”##
! No#"schizophrenic#classes”#doing#more#than#one#thing#! No#"12Dpage#methods"#
*#Code%Complete,#Steve#McConnell,#1993,#p.#81.#This0concept0was0first0described0by0Larry0Constan+ne0in01975,0but0we0like0McConnell’s0defini+on0best.0
c#
Paradigm00PaKerns0
Wisdom0Principles0 Prac+ces0
Quali+es##
30# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Strong#Cohesion##
! Class#Cohesion##– Class#has#a#single#responsibility#– Everything#"about"#fulfilling#that#responsibility#
! Method#Cohesion#– Each#method#fulfills#only#one#aspect#of#class#responsibility#– Prac8ce:#Programming#by#inten8on#(next#slide)#
c#
Paradigm00PaKerns0
Wisdom0Principles0 Prac+ces0
Quali+es##
Page 18
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
31# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Programming#by#Inten8on#
public void printReportOfEmployeesOfCustomer (String CustomerID) { Employee[] emps = getEmployees(CustomerID); if(needsSorting(emps)) sortEmployees(emps); printHeader(CustomerID); printFormattedEmployees(emps); printFooter(CustomerID); paginate(); }
"Private"* Methods
"Sergeant" Method
C#/Java/…
*Note:#These#methods#may#not#be#literally#private,#as#we#may#need#to#make#some#of#them#public#or#protected#for#tes8ng.##But#we#treat0them0as0private#from#client#objects,#to#limit#coupling.#
32# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Alterna8ve#Methods#(Separa8on#of#Concerns)###
public void printReportOfEmployeesOfCustomer (String CustomerID) { Employee[] emps = getEmployees(CustomerID); printReport(CustomerID, emps); } private void printReport(String CustomerID, Employee [] emps) { sortEmployees(emps); printHeader(CustomerID); printFormattedEmployees(emps); printFooter(CustomerID); paginate(); } private void sortEmployees(Employee [] emps){ if(needsSorting(emps)) doSortEmployees(emps); }
C#/Java/…
Page 19
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
33# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Programming#by#NonDInten8on#
public void printReportOfEmployeesOfCustomer (String CustomerID) { // Get Employees Employee[] emps …Make series of calls to get employees // Sort Employees … Series of calls to sort // Print Header … Series of calls //… and so forth for lots of lines }
C#/Java/…
34# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Programming#by#Inten8on#
void Report::printReportOfEmployeesOfCustomer (string CustomerID) { vector<Employee> emps = getEmployees(CustomerID); if(needsSorting(emps)) sortEmployees(emps); printHeader(CustomerID); printFormattedEmployees(emps); printFooter(CustomerID); paginate(); }
Private Methods
"Sergeant" Method
C++
*Note:#These#methods#may#not#be#literally#private,#as#we#may#need#to#make#some#of#them#public#or#protected#for#tes8ng.##But#we#treat0them0as0private#from#client#objects,#to#limit#coupling.#
Page 20
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
35# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
What#Programming#by#Inten8on#Gets#You#
! Method#Cohesion#! Separa8on#of#concerns#
– "Sergeant"#method#calls#other#methods#– Private#methods##implement#details#
! Clarity##– Clear#code#beWer#than#comments##
! Ease'in'finding/forming'certain'pa*erns'! No#extra#work#is#required#
36# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Coupling##
! Coupling###– “strength#of#connec8on#between#two#rou8nes#[or#classes]”#
! Object#can#be##– Loosely#coupled##
! No#dependence#on#other#implementa8ons#
! (Also#called0inten+onal0coupling)0– Tightly#coupled##
! Objects#are#interdependent;#– Change#one#thing;#other#things#change#unpredictably#
! (Also#called#accidental0coupling)#
c#
Paradigm00PaKerns0
Wisdom0Principles0 Prac+ces0
Quali+es##
*#Code%Complete,#Steve#McConnell,#1993,#p.#81.#This0concept0was0first0described0by0Larry0Constan+ne0in01975,0but0we0like0McConnell’s0defini+on0best.0
Page 21
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
37# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Coupling#To#Data#
Global#Data#
Func8on#One#
Func8on#Two#
Func8on#Three#
AWributes#
Method#One#
Method#Two#
Method#Three#
Class#
38# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Coupling#To#Other#Classes#
MyClass# YourClass#HerClass#
HisClass#Hard#to#test#Need#to#instan8ate#many#classes#Too#coupled##
Page 22
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
39# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
No#Redundancy#
! "One#Rule#in#One#Place"#! Example#of#viola8on:##Y2K#! Redundancy#can#be#more#than#state##
– E.g.#.#redundant#rela8onships#! Redundancy#causes#maintenance#problems#
! Before#copying#and#pas8ng,#ask#why?##
c#
Paradigm00PaKerns0
Wisdom0Principles0 Prac+ces0
Quali+es##
40# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Redundancy#D#Shalloway’s#Law#
! From#Al#Shalloway#(CEO#of#Net#Objec8ves)##
! “When#N#things#need#to#change#and#N>1,#Shalloway#will#find#at#most#ND1#of#these#things.”#
#
! Shalloway’s'Principle:#“Avoid#situa8ons#where#Shalloway’s#Law#applies”#
Page 23
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
41# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Encapsula8on#
! Hide##– Data#– Implementa8on#
! Other#encapsula8on:#– Type#
! Interfaces#hide#their#implemen8ng#classes#– Design#
! Using#factory#decouples#clients#from#implemen8ng#classes#
! Details#expanded#in#next#slides##
c#
Paradigm00PaKerns0
Wisdom0Principles0 Prac+ces0
Quali+es##
42# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Encapsulate#by#Policy,#Reveal#by#Need#
! What#is#encapsulated#is#– Decoupled#– Freely#changeable#
! Never#know#what#might#want#change#
! Easier#to#deDencapsulate#than#encapsulate#later#– So#encapsulate##
#
Page 24
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
43# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Abstrac8on#
! Abstrac8on#encompasses#encapsula8on#– Think#about#what#you#want#done,#not#how#you#want#it#done##
! “When#You’re#Abstract,#Be#Abstract#All#the#Way”#– Never#use#a#primi8ve#(except#in#constructors)#
! Example#next#page##
Paradigm00PaKerns0
Wisdom0Principles0 Prac+ces0
Quali+es##
44# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Dollar#Abstrac8on#
! Dollar#as#double##– double#interestRate;##– double#balance;#– double##interest#=#balance#*#interestRate#;#
! Dollar#class###– Dollar#mul8plyBy(Percentage#p)#
– Dollar#add(Dollar#other)#– Dollar#mul8plyBy(Dollar#d);#
– Dollar#add(Percentage#p);##Percentage#interestRate;#
Dollar#balance;##
Dollar#interest#=#balance.mul8plyBy(interestRate);##
#
Page 25
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
45# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Observa8on#
! Reversible#changes#are#o_en#not#equal#in#difficulty#! Usually#easier#to#deDobjec8fy#for#performance#than#it#is#to#objec8fy#for#code#quality##
! Example:#– Dollar#balance#"#double#balance;##
– double#balance##"#Dollar#balance;#
46# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Redundancy#
Class A
-Redundant Issue
Class B
-Redundant Issue
Class A and Class B:
Have redundant state or functionality
Redundant issue inside each class
How to resolve redundancy?
c#
Paradigm00PaKerns0
Wisdom0Principles0 Prac+ces0
Quali+es##
Page 26
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
47# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
It#Depends!*#
Depends#on#rela8onship#between#classes#– Conceptual?###
! Are#A#and#B#varia8ons#of#common#concept?#
or#– Rela8onship#of#consistent#use?###
! A#and#B#have#a#need#that#is#resolvable#in#a#common#way?#
Class A
-Redundant Issue
Class B
-Redundant Issue
*#©2007#All#Consultants#Everywhere#
48# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Using#Inheritance#
Class A Class B
Inheritance
Classes coupled to superclass
SuperClass
#Redundant Issue Conceptual
Concrete
Page 27
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
49# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Using#Delega8on#
Class A
Class B
Delega+on.##
Class C
Redundant Issue
50# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Comparing#These#Op8ons#
! Inheritance:#– May#not#be#possible###
! Classes#may#already#have#superclass##
– May#make#superclass#less#cohesive#
! Delega8on:#– Available#if#other#en88es#need#behavior#
! Favor'delegaAon'over'inheritance''(GOF)''Paradigm00PaKerns0
Wisdom0Principles0 Prac+ces0
Quali+es##
Page 28
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
51# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Testability#
! Difficult#to#unitDtest#code#is#o_en:#– Tightly#Coupled#
! “I#cannot#test#this#without#instan8a8ng#half#the#system"#
– Weakly#Cohesive#! #"This#class#does#so#much,#the#test#will#be#enormous#and#complex!"#
– Redundant#! #"I'll#have#to#test#this#in#mul8ple#places#to#ensure#it#works#everywhere"#
c#
Paradigm00PaKerns0
Wisdom0Principles0 Prac+ces0
Quali+es##
52# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
The#Role#of#Testability#
! Unit#tes8ng#is#good#! If##you#don’t#do#unit#test##
– Always#ask#"if#I#were#to#test#this,#how#would#I#do#it?"#– If#design#is#hard#to#test##
! Ask#"why#isn't#this#more#testable?"#
! It's#a#significant#trim#tab#(see#next#slide)#
c#
Paradigm00PaKerns0
Wisdom0Principles0 Prac+ces0
Quali+es##
Page 29
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
53# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Trim#Tabs#
"If you try to change the course of a supertanker by pushing at the bow you will not see any change.
If you push on the rudder your chances of changing the course of the supertanker are guaranteed, but the amount of energy needed is still prohibitive.
To be the most effective we need to push on the trim tabs, those small fins on the end of the rudder.
By moving them, the rudder in turn moves and the tanker makes its turn.”
R. Buckminster Fuller "Critical Path"
~2 54# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Standards#for#High#Quality#Code#(Review)#
High#quality#code#(in#order#of#importance):#! Testable''! Contains#no#redundancy''! Inten8onal#coupling,#strong#cohesion,#encapsulaAon'! Clarity'
– Inten8onDrevealing#names#
– Adhere#to#a#coding#standard#
Page 30
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
55# ### #16#October#2013#
A'Design'Exercise''
56# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Exercise##
! Exis8ng#Chip#object#– Gets#status#of#hardware#– Encrypts#status##– Sends#status#to#monitoring#applica8on#
! Now#need:#– Different#encryp8on#algorithms##
! For#different#customers#
! Or#perhaps#different#8me##
! How#can#we#can#handle#this#varia8on?#
Chip
+getAndSendStatus() -getStatus() -encrypt() -send()
-ChipID:String
Note:0I0am0not0asking0for0the0best0way0to0handle0this,0just0for0the0possible0ways0
Please#don't#turn#the#page#un8l#instructed#to#do#so…#
Page 31
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
57# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Blank#Slide#
! One#more#uninten8onally#blank#slide#
58# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Blank#Slide#
! Another#inten8onally#blank#slide#
! Don’t#look#ahead#
Page 32
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
59# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Blank#Slide#
! S8ll#another#inten8onally#blank#slide#
60# ### #16#October#2013#
AlternaAves'Approaches'To'Design'Exercise'
Page 33
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
61# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Different#Strategies#to#Follow#
! Best/Worst#Case##– Everyone#can#upgrade#to#the#new#encryp8on#
! Copy#and#paste##– Start#with#fresh#code,#just#make#needed#changes#
! Use#a#switch##– Add#switch#to#exis8ng#code#that#specifies#encryp8on#
! Inheritance##– Specialize##class#containing#encryp8on#code#– Override##encryp8on#method#to#use#new#encryp8on#
! Delega8on#– Encryp8on#code#in#own#class##– Different#versions#of#encryp8on#class.###– Clients#refer#to#appropriate#encryp8on#object#
! Func8on#pointers#in#C++;##delegates#in#C##62# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Ways#to#Handle#New#Func8on:#Switches#
! Chip#has#switch#based#on#value#given#by#Client#– Pro:##
! Simple,#obvious#implementa8on#
– Con:##! If#new#encryp8on#algorithm#
– Must#maintain#Chip#
! Cohesion#in#Chip#is#weakened#! May#get#“switch#creep”#
– Switches#are#not#a#good#longDterm#solu8on#
Page 34
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
63# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Switch#Creep#
switch (nation) {!!case US:!! !// us version!!case MEXICO:!! !// Mexican version!
!case CANADA:!! !// Canadian version!
!!
switch (nation) {!!case US:!! !// us version!!case MEXICO:!! !// Mexican version!!case CANADA:!! !// Canadian version!
}!!
Pseudocode
64# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Ways#to#Handle#New#Func8on:#Inheritance#
! Subclass#Chip:#– Chip#has#original#encryp8on#(64#bit)#– Subclass#is#Chip128E#
! Or#Make#Chip#an#abstract#class#– Implemen8ng#subclasses:#
! Encrypt#0##(no#encryp8on)#! Encrypt#64#! Encrypt#128#
– Most#func8onality#inherited#! Override#encrypt()#
Chip + getAndSendStatus() # encrypt()
Chip64E # encrypt() Chip128E
# encrypt() Chip0E
# encrypt()
Page 35
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
65# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Problems#With#Inheritance#
! Inheritance#works##for#one#varia8on#– Not#for#two#
! E.g.#what#if#sending#also#varies?###! Subclassing#is#sta8c##! How#change#Chip#from#Encrypt64#to#Encrypt128?#
– Need#to#transfer#internal#state##
66# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Combinatorial#Explosion#
Chip + getAndSendStatus() # encrypt()
Chip64E # encrypt() Chip128E
# encrypt()
# send()
# send() # send()
Chip128ETCP Chip128EFTP # send() # send()
Chip64ETCP Chip64EFTP # send() # send()
Redundancies
Cohesion getting worse
and worse
-ChipID
Page 36
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
67# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Delega8on#
Chip + getAndSendStatus() # encrypt()
PGP64 +encrypt()
PGP128 +encrypt()
Encryptor +encrypt()
-myEncrypt
Paradigm00PaKerns0
Wisdom0Principles0 Prac+ces0
Quali+es##
68# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Delega8on#Scales#
Chip
+ getAndSendStatus() # encrypt() PGP64
+encrypt() PGP128
+encrypt()
Encryptor +encrypt()
-mySend -myEncrypt
TCPIP +send()
FTP +send()
Sender +send()
# send()
Page 37
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
69# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Refactoring:##The#Tradi8onal#View#
! Refactoring#usually#is#for#legacy#code#– Seen#as#cleaning#up#bad#code#– True,#but#not#complete#
! Refactor#code#to#issue#that#has#become0a0varia+on0– Improvement#in#light#of#new#requirements#
“Adventure”# hWp://benfry.com/distellamap/# 70# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Refactoring#(1)#
public class Chip { private String chipID; public Chip(String aChipID) { this.chipID = aChipID; } public void getAndSendStatus() { String status = getStatus(chipID); String encryptedStatus = encrypt(status); send(encryptedStatus); } private String getStatus(String chipID) { // get status from the real chip } private String encrypt(String status) { // encryption algorithm here } private void send(String status) { // sending behavior here }
}
Original'code'
Page 38
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
71# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Refactoring#(2)#
// All elided code is unchanged from previous slide public class Chip {
private String chipID; private Encrypt myEncrypt; public Chip(String aChipID) { this.chipID = aChipID; this.myEncrypt = new PGP64(); } private String encrypt(String status) { return myEncrypt.encrypt(status); }
}
Delega8on#“Extract#Class”#
and#“Extract#Interface”#
72# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Enhancement###
Adding'new'encrypAon'is'enhancement,'not'refactoring'
Page 39
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
73# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Factory###
Encryptor getEncryptor(CustomerType customer) { switch (customer)
{ case C1:
return new PGP64(); case C2:
return new PGP128(); default:
return new PGP0(); } }
//In Chip
public Chip(String aChipID, Customer customer) { this.chipID = aChipID;
this.myEncrypt = getEncryptor(customer); }
74# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Strategy#Injec8on##(1)#
• Constructor injection class Chip {
private Encryptor enc; public Chip(Encryptor encrypt) {
this.enc = encrypt; }
private void encrypt() { this.enc.encrypt(); } public void getAndSendStatus() { encrypt() // and other calls
}
Page 40
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
75# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Strategy#Injec8on##(2)#
• Parameter injection class Chip {
public Chip() { }
public void getAndSendStatus(Encryptor enc) {
enc.encrypt(); // and other calls }
}
76# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Strategy#Injec8on##(3)#
• Setter injection class Chip { private Encryptor enc;
public Chip() { } public void setEncryptor(Encryptor encrypt) { enc = encrypt; } public void getAndSendStatus() {
enc.encrypt(); // and other calls }
}
Page 41
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
77# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Injec8on#With#Mul8ple#Strategies###
// Multiple strategies, constructor injection // Chip has constructor Chip(Encryptor e, Sender s) Chip getChip(CustomerType customer)
{ switch(customer) { case C1: return new Chip(new PGP64(), new TCPIP()); case C2: return new Chip(new PGP128(), new TCPIP()); default: return new Chip(new PGP0(), new FTP()); } }
78# ### #16#October#2013#
Advice'from'the'Gang'of'Four'
Page 42
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
79# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Gang#of#Four#Gives#Us#Guidelines*#
! Open/Closed'Principle'! Design'to'interfaces'! Favor'delegaAon'over'class'inheritance'! Encapsulate'concept'that'varies''
#
*'Gamma,#Helms,#Johnson,#Vlissides:#The#authors#of#Design%Pa2erns:%Elements%of%Reusable%Object<Oriented%Design%
Paradigm00PaKerns0
Wisdom0Principles0 Prac+ces0
Quali+es##
80# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
The#OpenDClosed#Principle#
! So_ware#en88es#should#be:#– Open#for#extension#– Closed#for#modifica8on##
! In#short:#– Design#modules#so#that#they#never#change##– Add#new#modules#to#handle#changed#requirements#– Not#always#achievable##
! Bertrand#Meyer:##– So_ware#en88es#(classes,#modules,#func8ons,#etc.)#should#be#open#for#
extension,#but#closed#for#modifica8on”#
! Ivar#Jacobson#:###– “All#systems#change#during#their#life#cycles.##This#must#be#borne#in#mind#
when#developing#systems#expected#to#last#longer#than#the#first#version”#A#good#ar8cle#on#the#OpenDClosed#Principle:#www.objectmentor.com/publica8ons/ocp.pdf#
c#
Paradigm00PaKerns0
Wisdom0Principles0 Prac+ces0
Quali+es##
Page 43
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
81# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Design#to#Interfaces#
InterfaceA
Impl1 Impl2 Impl3
Interface B
Impl4 Impl5
Relationship
Relationship
Want#1→1#or#1→many#rela8onships#between#abstrac8on#
Not#n→m#rela8onships#between#implementa8ons#
Paradigm00PaKerns0
Wisdom0Principles0 Prac+ces0
Quali+es##
82# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Favor#Delega8on#Over#Inheritance#
! Define#interface#encapsula8ng#varia8on#! Delegate#to#concrete#class#implemen8ng#interface#
1. Decoupling concepts 2. Defer decisions until runtime 3. Small performance hit
Delegation
The "Strategy Pattern"
Chip + getAndSendStatus() # encrypt()
PGP64 +encrypt()
PGP128 +encrypt()
Encryptor +encrypt()
-myEncrypt
Paradigm00PaKerns0
Wisdom0Principles0 Prac+ces0
Quali+es##
Page 44
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
83# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Treat#Conceptually#Similar#Things#the#Same#Way#
! Deal#with#things#at#an#abstract#level#! Encapsulate#that#which#varies#
Impl4
AbstractionA
Impl1 Impl2 Impl3
Client
Closed is abstraction
Open are implementations
Paradigm00PaKerns0
Wisdom0Principles0 Prac+ces0
Quali+es##
84# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Find#What#Varies#and#Encapsulate#It#
! GoF#meant#a#varying#anything:0– Varying#design#– Varying#object#crea8on#– Varying#rela8onships#(1D1,#1Dmany)#– Varying#sequences#and#workflows#– Etc…#
Page 45
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
85# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
This#Advice#Promotes#Quality#
Cohesive#
Decoupled#Reusable#
(eliminates#Redundant#Implementa8on)#
Encapsulated#
86# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Design#PaWerns#Are#Examples0
! Each#paWern:#– Example#of#a#design#following#general#advice#
– Discovered,#not#invented#– Example#in0a0given0context#
Page 46
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
87# ### #16#October#2013#
The'Strategy'Pa*ern'
88# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
The#Strategy#PaWern#
! Issue:#– Need#different#behavior#at#different#8mes#
! GoF#Intent:##– Define#a#family#of#algorithms,#encapsulate#each#one,#and#make#them#interchangeable##
– Algorithm#vary#independently#from#clients#using#it#*#
#
*Design%Pa2erns,%Elements%of%Reusable%Object<Oriented%So?ware,#Gamma,#Helm,#Johnson,#Vlissides#
Paradigm00PaKerns0Wisdom0
Principles0 Prac+ces0
Quali+es##
Page 47
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
89# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
The#Canonical#Strategy#PaWern#
Java/C# // in Client: Strategy myStrategy=
Factory.getStrategy() . . . myContext.request( myStrategy) // in Context: request ( Strategy myStrategy) { myStrategy.algorithm() }
StrategyA + algorithm()
StrategyB + algorithm()
Context + request(Strategy)
Strategy + algorithm()
Client
C++ // in Client: Strategy *myStrategy=
Factory.getStrategy() . . . myContext.request( myStrategy) // in Context Context::request ( Strategy myStrategy) { myStrategy->algorithm() }
90# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Handling#Varia8ons#
! Factory#creates#different#objects#having#common#interface##(polymorphism)##– Factory#is#cohesive##D##only#deals#with#instan8a8on#
! Client#decoupled#from#actual#objects#
Page 48
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
91# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Strategy#PaWern#with#a#Factory#
*#
92# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Code#Examples#for#this#Approach#
class Client () { Encryptor myEncrypt; myEncrypt= Factory.getEncryptor(); // get proper derivation to use
Chip myChip= new Chip(); myChip.getAndSendStatus(myEncrypt); } class Chip () { //... public void getAndSendStatus( Encryptor anEncrypt) {
//... anEncrypt.doEncrypt(s); // ... } } // Encrypt is an interface or abstract class with a doEncrypt method.
// Have different classes implement this, each with a doEncrypt method.
C#/Java
~2
Page 49
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
93# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Code#Examples#for#this#Approach#
public void main () { Encryptor * myEncrypt; myEncrypt= Factory::getEncryptor(); // get proper derivation to use Chip myChip; myChip->getAndSendStatus( myEncrypt); } // in Chip.h class Chip () { public void getAndSendStatus( Encryptor *); } // in Chip.cpp ... void Chip::getAndSendStatus( Encryptor *anEncrypt) { ... anEncrypt->doEncrypt(s); ... } } // Encrypt is an interface or abstract class with a doEncrypt method. // Have different classes implement this, each with a doEncrypt method.
C++
~2 94# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
What#Happens#Now#with#Changing#Requirements#
! If#new#encryp8on#requirement:##– 1.)#Create#new#class#implemen8ng#encryp8on#
– 2.)#Modify#Factory#to#return#new#class#– 3.)#Nothing#else!#
Page 50
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
95# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Creeping#Changes#(Review)#
function(a, b) { if (a) {
if (b) { Do_another_thing:; //… }
else { Do_one_more_thing; //.. }
} else {
Do_this; Do_that; Do_something_else; }
}
96# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Switch#Version#(1)#enum WhatToDo {Do_original, Do_another_thing, Do_one_more_thing}; class DoSomething { static void process(WhatToDo wtd) { switch(wtd) { case Do_original: Do_this; Do_that; Do_something_else; break; case Do_another_thing:
Do_another_thing; //.. break;
case Do_one_more_thing: Do_one_more_thing; //… break;
} }
Page 51
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
97# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Switch#Version#(2)#
// Separate what to do from doing it WhatToDo factory(a, b) { if (a){
if (b) return Do_another_thing;;
else return Do_one_more_thing; }
else return Do_original; }
class Client {
WhatToDo wtd = factory(a, b); DoSomething.process(wtd); }
98# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Switch#Version#with#Func8ons###class DoSomething { static void process(WhatToDo wtd) { switch(wtd) { case Do_original: DoOriginal(); break; case Do_another_thing:
DoAnotherThing(); break; case Do_one_more_thing: DoOneMoreThing(); break; } } static void doOriginal() { Do_this; Do_that; Do_something_else; } static void doAnotherThing() {
Do_another_thing; //.. } static void DoOneMoreThing() {
Do_one_more_thing; //… }
Page 52
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
99# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Convert#To#Strategy#
! Separate#what#to#construct#from#using#it##– Separate#policy#from#implementa8on#– Create#factory#to#return#implementa8on#of#interface#
#interface DoSomething{ void process(); };
100# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Convert#To#Strategy#(2)#class Do_original implements DoSomething { void process()
Do_this; Do_that; Do_something_else; } };
class Do_another_thing implements DoSomething { void process() { Do_another_thing; //… } };
class Do_one_more_thing implements DoSomething { void process() { Do_one_more_thing; //… } };
Page 53
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
101# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Convert#To#Strategy#(2)#
DoSomething factory(a, b) { if (a){ if (b)
return new Do_another_thing(); else return new Do_one_more_thing(); } else return new Do_original();
} class Client { public void some_method() { DoSomething ds = factory(a, b); ds.process(); } }
102# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Select#Strategy#with#a#Table#
A# B# Return##
True# true# Do_another_thing#
True# false# Do_one_more_thing#
False# true# Do_original#
False# False# Do_original#
Page 54
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
103# ### #16#October#2013#
The'Template'Method'Pa*ern'
~2
Paradigm00PaKerns0Wisdom0
Principles0 Prac+ces0
Quali+es##
104# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
The#Template#Method#PaWern#
! Issue:#– Abstract#common#theme#from#cases#with#different#implementa8ons#
! GoF#Intent:##– Define#skeleton#of#an#algorithm#in#an#opera8on,#deferring#some#steps#to#subclasses.###
– Template#Method#lets#subclasses#redefine#certain#steps#of#an#algorithm#without#changing#the#algorithm’s#structure*#
! Analogy##– Hollywood#–#“Don’t#call#us,#we’ll#call#you”##
*Design%Pa2erns,%Elements%of%Reusable%Object<Oriented%So?ware,#Gamma,#Helm,#Johnson,#Vlissides#
~2
Page 55
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
105# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Print#Report##
class Report { public void printReportOfEmployeesOfCustomer (String CustomerID) { Employee[] emps = getEmployees(CustomerID); if(needsSorting(emps)) sortEmployees(emps); printHeader(CustomerID); printFormattedEmployees(emps); printFooter(CustomerID); paginate(); } //.. Implementation methods here }
106# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Commonali8es#/#Variabili8es#
~2
Commonality#
Variabili8es#
printHeader(CustomerID);
printFooter(CustomerID);
printHeader(CustomerID); // Brief Header // Full Header
printFooter(CustomerID); // Brief Footer // Full Footer
Page 56
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
107# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Template##PaWern#
BriefHeaderReport
#printHeader();
#printFooter();
FullHeaderReport
#printHeader();
#printFooter();
Report +printReportOfEmployeesOfCustomer()
#getEmployees(CustomerID);
#sortEmployees();
#printHeader();
#printFormattedEmployees();
#printFooter();
#paginate();
108# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Template#Method#Code#Example#
abstract class Report { public void printReportOfEmployeesOfCustomer (String customerID) { // … printHeader(customerID); printFooter(customerID); } abstract protected void printHeader(ID id); abstract protected void printFooter(ID id); } class BriefHeaderReport extends Report { protected void printHeader(ID id) { //. Code here } protected void printFooter(ID id) { //.. Code here } }
Page 57
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
109# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
"Canonical"#Template#Method#
Client
ConcreteClassB
#Operation1() #Operation2()
TemplateMethod: … Operation1() … Operation2() …
AbstractTemplate +TemplateMethod()
#Operation1() #Operation2()
~2
ConcreteClassA
#Operation1() #Operation2()
110# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Strategy##PaWern#
BriefHeader
printHeader();
printFooter();
FullHeader
#printHeader();
printFooter();
Report +printReportOfEmployeesOfCustomer()
#getEmployees(CustomerID);
#sortEmployees();
#printHeader();
#printFormattedEmployees();
#printFooter();
#paginate();
Header
printHeader();
printFooter();
Page 58
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
111# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Exercise#
! There#could#be#a#separate#strategy#for#both#header#and#footer.###
! What#are#the#tradeoffs#between#the#Template#Method#and#the#two#versions#of#the#Strategy#paWern#(header/footer#in#one,#header/footer#separate)##
112# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Template#Example#in#MFC#
Windows#System## Applica8on##ac8vate#
Window##ac8vate()##{draw();}#draw();###close()#minimize()#//#fi_y#more#(with#default#implementa8on)##
MyWindow##draw()#{#//#mydrawing;}##
Page 59
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
113# ### #16#October#2013#
Design'Pa*erns'
Paradigm00PaKerns0Wisdom0
Principles0 Prac+ces0
Quali+es##
114# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
A#PaWern#in#Carpentry#
! Two#carpenters#are#building#a#chest#of#drawers#! One#says#to#the#other:#“should#we#build#the#joint#by#first#cuÑng#down,#then#cuÑng#up#at#a#45#degree#angle...”#
! “then#back#down#and#back#up### #the#other#way,#then#back#down”#
! “And#keep#this#up#un8l#done”#! This#is#“doveDtail#joint”##
Page 60
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
115# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
DoveDTail#
116# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
A#Miter#Joint#
Commonly#used#in#picture#frames#
Page 61
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
117# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
PaWerns#Work#At#All#Levels#
Dovetail' Miter'
Forces' Strong,#HighDCost,#Decora8ve,#Humidity#Tolerant#
Weak,#Cheap,#Fast,#Good#for#Picture#Frames#
Design' Interlaced#joint# Single#AbuÑng#Cut#
ImplementaAon' Cut#teeth,#.5"#long,#.4"#deep,#match#teeth#to#gaps#
45#degree#angle#cut#aWached#with#staple#or#other#spanning#connector#
118# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Common#Reasons#to#Study#PaWerns#
! ReDuses#others’#experience#– some8mes#results#in#quick#solu8on#
! Designs#improved#for#modifiability#– Embrace#change#
! Use#common#terminology#– Improve#and#elevate#communica8on#
! PaWerns#are#great#examples#of#powerful#OO#
Page 62
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
119# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
What#Are#PaWerns?#
! PaWern:#– Collec8on#of#proven#prac8ces#for#a#recurring#problem#in#a#given#context#
! Design#paWerns##– Describe#rela8onships#between#en88es#(objects)#in#a#problem#domain#
! PaWerns#– Handle#varia8ons#in#behavior#– Use#interfaces#
! PaWerns#have#forces##– Contextual#forces#–#to#determine#what#paWern#to#use#– Implementa8on#forces#–#how#to#create#the#paWern##– Consequen8al#forces#–#what#happens#when#paWern#is#used##
! PaWerns#emphasize#importance#of#abstrac8ons#– …but#do#not#address#how#to#iden8fy#the#right#ones…#
120# ### #16#October#2013#
AbstracAon'
Paradigm00PaKerns0
Wisdom0Principles0 Prac+ces0
Quali+es##
Page 63
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
121# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Consider#These#
Mop'''''''''''''''''''''''''Broom''''''''''''''Sponge'
The#same?##Different?#
122# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
“It0Depends!”#
! As#specific#objects:##– Different#
! As#a#concept#(abstrac8on):#– All#Cleaning#Tools#
! Are#there#other#abstrac8ons#with#different#commonality?##
! Which#abstrac8ons#are#useful?#####
Page 64
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
123# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Various#Concepts#
Cleaning#Tool#cleanSomething()#
Mop#
Floor#Cleaning#Tool#cleanFloor()#
Water#Cleaning#Tool#removeWater()#
Mop#Mop#Broom# Broom#Sponge# Sponge#
ItemsToStore#size()#
Mop# Broom# Sponge#
ItemsForSale#price()#
Mop# Broom# Sponge#
All#Yellow#Items#
124# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
High#Abstrac8on##
! Higher#abstrac8ons#are#longer#life##– (But#can#be#less#useful)#
! Example:#– Abstrac8on###
! Automobile##– Prepare#for#following##– Follow#a#course###
! Implementa8ons:#– Turn#on#with#key##/###Push#a#buWon##– Steer#with#wheel,#speed#with#pedals#/###Use#a#joys8ck###
Page 65
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
125# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
What#Is#the#Right#Abstrac8on?##
! The#United#Kingdom#"could#be#seen#as#economy#by#economists,#a#society#by#sociologists,#a#threaded#chunk#of#nature#by#conserva8onists,#a#tourist#aWrac8on#by#some#Americans,#a#military#threat#by#rulers#of#the#Soviet#Union,#and#the#green,#green#grass#of#home#to#the#more#roman8c#of#us#Britons".#
! Flood#and#Carson#! "Why#is#a#light#bulb#like#Doonesbury?"#
– Neither#one#can#whistle#
126# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
CommonalityDVariability#Analysis#
! Abstrac8on##focuses#on#commonality#(general)#! DeDemphasize#variable#details##(specifics)#.#! Acknowledgement:##
– Commonality#–#Variability#Analysis#in#James#Coplien’s#Mul8Dparadigm#Design#for#C++#
His#thesis#is#on#line#at#hWp://www.netobjec8ves.com/download/CoplienThesis.pdf#
c#
Paradigm00PaKerns0
Wisdom0Principles0 Prac+ces0
Quali+es##
His#thesis#is#on#line#at:#hWp://www.netobjec8ves.com/files/CoplienThesis.pdf#(link#is#caseDsensi8ve)#
Page 66
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
127# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Commonali8es#and#Variability#
! Commonali8es#can#define#basic#domain#concepts#(abstrac8ons)#– Recognized#from#experience#– Learned#through#analysis#(abstracted)#
! Variability#is#varia8on#of#commonality#(abstrac8on)##
*'MulB<Paradigm%Design%in%C++,#Jim#Coplien#
128# ### #16#October#2013#
The'Bridge'Pa*ern'
Page 67
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
129# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
The#Bridge#PaWern#
! GoF#Intent:##– DeDcouple#an#abstrac8on#from#its#implementa8on#so#that#the#two#can#vary#independently#*##
! First#an#example##
*Design%Pa2erns,%Elements%of%Reusable%Object<Oriented%So?ware,#Gamma,#Helm,#Johnson,#Vlissides#
Paradigm00PaKerns0Wisdom0
Principles0 Prac+ces0
Quali+es##
130# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Rectangle#Drawing#Program#
Rectangle + draw() # drawLine(x1,y1,x2,y2)
DP1 + draw_a_line(x1,y1, x2,y2) + draw_an_arc(x, y, r, a1, a2)
Client
V1Rectangle # drawLine(x1,y1 x2,y2)
V2Rectangle # drawLine(x1,y1 x2,y2)
DP2 + drawline(x1,x2,y1,y2) + drawarc(r, x, y, a1, a2)
Page 68
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
131# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Code#Example#abstract class Rectangle { private double_x1, _y1, _x2, _y2; public Rectangle(double x1, double y1, double x2, double y2){ .. } void public Draw () { DrawLine(_x1,_y1,_x2,_y1); DrawLine(_x2,_y1,_x2,_y2); DrawLine(_x2,_y2,_x1,_y2); DrawLine(_x2,_y1,_x1,_y1); } abstract void DrawLine( double x1, double y1, double x2, double y2); } class V1Rectangle : Rectangle { void override DrawLine( double x1, double y1, double x2, double y2) { DP1.draw_a_line( x1,y1,x2,y2); } } class V2Rectangle : Rectangle { void override DrawLine(double x1, double y1, double x2, double y2) { DP2.drawline( x1,x2,y1,y2); } }
C#
132# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Code#Example#
abstract class Rectangle { private double_x1, _y1, _x2, _y2; public Rectangle(double x1, double y1, double x2, double y2){ .. } void public draw () { drawLine(_x1,_y1,_x2,_y1); drawLine(_x2,_y1,_x2,_y2); drawLine(_x2,_y2,_x1,_y2); drawLine(_x2,_y1,_x1,_y1); } abstract void drawLine( double x1, double y1, double x2, double y2); } class V1Rectangle extends Rectangle { drawLine( double x1, double y1, double x2, double y2) { DP1.draw_a_line( x1,y1,x2,y2); } } class V2Rectangle extends Rectangle { drawLine(double x1, double y1, double x2, double y2) { DP2.drawline( x1,x2,y1,y2); } }
Java
Page 69
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
133# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Code#Example#
class V1Rectangle : public Rectangle { … } class V2Rectangle : public Rectangle { … } void Rectangle::draw () { drawLine(_x1,_y1,_x2,_y1); drawLine(_x2,_y1,_x2,_y2); drawLine(_x2,_y2,_x1,_y2); drawLine(_x1,_y2,_x1,_y1); } void V1Rectangle::drawLine (double x1, double y1, double x2, double y2) { DP1::draw_a_line( x1,y1,x2,y2); } void V2Rectangle::drawLine (double x1, double y1, double x2, double y2) { DP2::drawline( x1,x2,y1,y2); }
C++
134# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Get#New#Requirements#
! Now#have#Circles#! Handle#similarly##
– Make##V1Circle#and##V2Circle#
! Decouple#client#from#specific#shapes##– Derive#specific#shapes#from#base#class#
Page 70
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
135# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Handling#New#Shape#Class#
Rectangle +draw()
Shape +draw()
Client
Circle + draw()
V1Rectangle # drawLine(x1, y1, x2, y2)
V2Rectangle # drawLine(x1, y1, x2, y2)
V1Circle #drawArc(x,y,r,a1,a2)
V2Circle # drawArc(x,y,r,a1,a2)
DP2 + drawline(x1, x2, y1, y2) + drawarc( r,x, y, a1,a2)
DP1 + draw_a_line(x1, y1, x2, y2) + draw_an_arc(x, y, r, a1, a2)
136# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Code#Example#
interface Shape { public void draw(); } abstract class Rectangle : Shape { private double _x1,_y1,_x2 _y2; public override void draw() { drawLine(_x1, _y1, _x2, _y1); drawLine(_x2, _y1, _x2, _y1); drawLine(_x2, _y2, _x1, _y2); drawLine(_x1, _y2, _x1, _y1); } abstract void drawLine( double x1, double y1, double x2, double y2); } } class V1Rectangle : Rectangle { public override void drawLine( double x1, double y1, double x2, double y2){ DP1.draw_a_line(x1,y1, x2, y2); } }
class V2Rectangle : Rectangle { public override void drawLine( double x1, double y1, double x2, double y2){ DP2.drawline(x1, x2, y1, y2); } } abstract class Circle : Shape { private double _x, _y, _r; public override void draw () { drawArc( _x, _y, _r, 0, 360); } abstract void drawArc( double x, double y, double r, double a1, double a2); } class V1Circle : Circle { protected override void drawArc(double x, double y, double r, double a1, double a2){ DP1.draw_an_arc(x,y,r,a1,a2); } } class V2Circle : Circle { protected override void drawArc(double x, double y, double r, double a1, double a2){ DP2.drawarc(_r,_x,_y,a1,a2); } }
C#
Page 71
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
137# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Code#Example#
interface Shape { public void draw(); } abstract class Rectangle implements Shape { private double_x1,_y1,_x2,_y2; public void draw() { drawline(_x1, _y1, _x2, _y1); drawline(_x2, _y1, _x2, _y1); drawline(_x2, _y2, _x1, _y2); drawline(_x1, _y2, _x1, _y1); } abstract void drawline( double x1, double y1, double x2, double y2); } class V1Rectangle extends Rectangle { public void drawline( double x1, double y1, double x2, double y2){ DP1.draw_a_line(x1, y1, x2, y2); } }
class V2Rectangle extends Rectangle { public override void drawLine( double x1, double y1, double x2, double y2){ DP2.drawline(x1, x2, y1, y2); } } abstract class Circle implements Shape { private double _x, _y, _r; public draw () { drawArc( _x, _y, _r, 0, 360); } abstract void drawArc( double x, double y, double r, double a1, double a2); } class V1Circle extends Circle { protected void drawArc( double x, double y, double r, double a1, double a2){ DP1.draw_an_arc(x,y,r,a1,a2); } } class V2Circle extends Circle { protected void drawArc( double x, double y, double r, double a1, double a2){ DP2.drawarc(_r,_x,_y,a1,a2); } }
Java
138# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Code#Example#
void Shape::draw () {} void Rectangle::draw () { drawLine(_x1,_y1,_x2,_y1); drawLine(_x2,_y1,_x2,_y2); drawLine(_x2,_y2,_x1,_y2); drawLine(_x1,_y2,_x1,_y1); } void V1Rectangle::drawLine ( double x1, double x2, double y1, double y2) { DP1::draw_a_line(x1,y1,x2,y2); } void V2Rectangle::drawLine ( double x1, double x2, double y1, double y2) { DP2::drawline(x1,x2,y1,y2); }
void Circle::draw () { drawArc( _x, _y, _r, 0, 360); } void V1Circle::drawArc( double x, double y, double r, double a1, double a2) { DP1::draw_an_arc(x, y, r, a1,a2); } void V2Circle::drawArc ( double x, double y, double r, double a1, double a2) { DP2::drawarc( r, x, y, a1, a2); }
C++
Page 72
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
139# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Redundant#Rela8onships#
Rectangle +draw()
Shape +draw()
Client
Circle + draw()
V1Rectangle # drawLine(x1, y1, x2, y2)
V2Rectangle # drawLine(x1, y1, x2, y2)
V1Circle #drawArc(x,y,r,a1,a2)
V2Circle # drawArc(x,y,r,a1,a2)
DP2 + drawline(x1, x2, y1, y2) + drawarc( r,x, y, a1,a2)
DP1 + draw_a_line(x1, y1, x2, y2) + draw_an_arc(x, y, r, a1, a2)
6264#
140# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Did#We#Resolve#the#Redundancy?#
Page 73
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
141# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Problems#with#this#Approach#
! Doesn’t#scale#well#– Another#Shape#"#3#*#2#implementa8ons#– Number#implementa8ons#=#########number#of#Shape#types#8mes#number#of#drawing#programs#
! Redundant#– Drawing#with#each#shape#involves#duplica8on#– Redundancies#between#V1Rectangle#and#V2Rectangle,#etc…#
! Confusing#and#complex#– Poor#cohesion#makes#classes#hard#to#follow#
142# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Intent#Makes#Sense#Now#
! GoF#Intent:##– DeDcouple#an#abstrac8on#from#its#implementa8on#so#that#the#two#can#
vary#independently#*##! Abstrac8on:##
– Main#enAty#that#client#is#aware#of.#– E.g.#Shape#
! Implementa8on:##– Way#that#main#en8ty#fulfills#one#aspect#of#its#responsibili8es.##– E.g.##drawing#behavior#–#Drawing#
! In#other#words:#– Way#to#add#new#Shapes#OR#new#Drawing#Programs#without#affec8ng#the#
other#
*Design%Pa2erns,%Elements%of%Reusable%Object<Oriented%So?ware,#Gamma,#Helm,#Johnson,#Vlissides#
Page 74
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
143# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Discovering#the#Bridge#PaWern#
! Discover#the#Bridge#paWern#by:#– Find#commonali8es#and#how#they#vary##– Represent#common#concepts#with#abstrac8ons#(interfaces)#– Make#concrete#class#for#each#varia8on##
! Then:#– Observe#how#abstrac8ons#relate#– Pick#rela8onship#with#beWer#code#quali8es#
144# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
We#Have#the#Following#Commonali8es#
! Shape#class#=#abstrac8on#with#varying#behavioral#implementa8ons#
! Commonality#Variably#Analysis#separates#issues#into#isDa#rela8onships#
Shape
+draw()
Drawing
+drawLine()+drawCircle()+drawArc()0
Page 75
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
145# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Derive#Varia8ons0
Shape
+draw()
Rectangle
+draw()
Drawing
+drawLine()+drawCircle()
V2Drawing
+drawLine()+drawCircle()
V1Drawing
+drawLine()+drawCircle()
Circle
+draw()
+drawArc()0
+drawArc()# +drawArc()#
146# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Determine#Remaining#Rela8onships0
Shape
+draw()
Rectangle
+draw()
Drawing
+drawLine()+drawCircle()
V2Drawing
+drawLine()+drawCircle()
V1Drawing
+drawLine()+drawCircle()
Circle
+draw()
Each side should "Design to Interfaces”
Which Way?
Page 76
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
147# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Use#Quali8es#to#Define#Rela8onship#
! Ways#the#two#sides#can#relate:#– Shapes#use#drawing#programs#
– Drawing#programs#draw#shapes#– Third#object##gets#shape#and#drawing#program##
! Which#way#is#beWer?#– Score#with#quali8es#– BeWer#quali8es#"#beWer#design##
148# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Another#Quality#D#Asser8veness##
! Asser8veness###– Don’t#ask#ques8ons#of#an#object##– Assert#that#an#object#should#do#something#
! Example#on#next#slide#
c#
Paradigm00PaKerns0
Wisdom0Principles0 Prac+ces0
Quali+es##
Page 77
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
149# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Inquisi8ve#
class Date { int getMonth(); int getDay(); int getYear(); }
Date d = new Date(); String output = d.getMonth() + “/” + d.getDay() + “/” +
d.getYear();
150# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Asser8ve#
class Date { String getAsString() { ] }
Date d = new Date(); String output = d.getAsString();
#
Page 78
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
151# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Scoring#–#Fill#It#In#
Shapes#use#DP# DP#given#Shape# 3rd#Module#
Loose#Coupling#
Strong#Cohesion#
No#Redundancy#
Encapsula8on#
Testable#
Asser8ve#
Focus#
152# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Shapes#Using#Drawing#Programs#
: Client : Rectangle : DP1
1: draw
2: drawLine
3: drawLine
4: drawLine5: drawLine
Page 79
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
153# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Drawing#Programs#Using#Shapes#
: Rectangle : Client : DP1
1: draw( Shape s)
2: What kind of shape?
3: I'm a rectangle
4: Give me your line 1 info
5: Draw it
6: Give me your line 2 info
7: Draw it
8: Give me your line 3 info
9: Draw it
10: Give me your line 4 info
11: Draw it
154# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Control#Program#Using#Shapes#
: Client : ControlPrgm
: Rectangle : DP1
1: draw( Shape, DP)
2: what kind of shape?
3: I'm a rectangle
4: give me your line 1 info
5: drawLine
6: give me your line 2 info
7: drawLine
8: give me your line 3 info
9: drawLine
10: give me your line 4 info
11: drawLine
Page 80
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
155# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Scoring#
Shapes#use#DP# DP#given#Shape# 3rd#Module#
Loose#Coupling# Yes# DPs#coupled#to#Shapes#
Module#coupled#to#Shapes#
Strong#Cohesion# Yes# DPs#concerned#with#Shapes#
Weak:#Shape#and#Draw#stuff#
No#Redundancy# Yes# Knowledge#of#shapes#duplicated#in#DPs#
Knowledge#of#shapes#duplicated#in#CP#
Encapsula8on# implementa8on#and#type#
implementa8on#only# implementa8on#only#
Testable# N#+#M# N#*#M# N#+#M#
Asser8ve# Yes# No# No#
Focus# Yes# Shapes#spread#out#a#liWle#
Yes#
Shapes using DPs wins! 156# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Add#the#Rela8onship#
Shape
+draw()
Rectangle
+draw()
Drawing
+drawLine()+drawArc()
1..1
1
DP2
+drawline()+drawarc()
V2Drawing
+drawLine()drawArc()
DP1
+draw_a_line()+draw_an_arc()
V1Drawing
+drawLine()+drawArc()
Circle
+draw()
drawing.drawLine()##
Page 81
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
157# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Illustra8ng#the#Separa8on#
Shape
+draw()
Rectangle
+draw()
Drawing
+drawLine()+drawArc()
1..1
1
DP2
+drawline()+drawarc()
V2Drawing
+drawLine()+drawArc()
DP1
+draw_a_line()+draw_an_arc()
V1Drawing
+drawLine()+drawArc()
Circle
+draw()
Abstraction
Implementation
158# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Example#Implementa8on##class Client { public static void Main (String argv[]) { Shape s1; Shape s2; Drawing dp; // See comments below to see // what gets returned dp= Factory.getDP(); s1= Factory.getShape(dp); dp= Factory.getDP(); s2= Factory.getShape(dp); s1.draw(); s2.draw(); } } // Factory: // 1st call: getDP returns V1Drawing // 1st call: getShape returns // new Rectangle(dp,1,1,2,2); // 2nd call: getDP returns V2Drawing // 2nd call: getShape returns // new Circle( dp,2,2,4);
interface Shape { public void draw(); } class Rectangle : Shape { private Drawing _dp; Rectangle (Drawing dp, double x1, double y1, double x2, double y2) { _dp = dp; _x1= x1; _y1= y1; _x2= x2; _y2= y2;} public override void draw () { _dp.drawLine(_x1, _y1, _x2, _y1); _dp.drawLine(_x2, _y1, _x2, _y2);
_dp.drawLine(_x2, _y2, _x2, _y1); _dp.drawLine(_x2, _y1, _x1, _y1); } }
C#
Page 82
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
159# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Example#Con8nued#
class Circle : Shape { private Drawing _dp; Circle (Drawing dp, double x, double y, double radius) { _dp = dp; _x= x; _y= y; _radius= radius; } public override void draw () { _dp.drawArc(_x,_y,_radius, 0, 360); } }
interface Drawing { void drawLine ( double x1, double y1, double x2, double y2); void drawArc(double x, double y,double radius, double fromAngle, doubletoAngle);} class V1Drawing : Drawing { public override void drawLine ( double x1, double y1, double x2, double y2) { DP1.draw_a_line( x1, y1, x2, y2); } public override void drawArc ( double x, double y, double radius, double fromAngle, double toAngle){ DP1.draw_an_arc( x, y,radius, fromAngle,toAngle); } }
C#
160# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Example#Con8nued#
class Rectangle : Shape { Rectangle : base(dp) ( Drawing dp, double x1, double y1, double x2, double y2) { _x1= x1; _y1= y1; _x2= x2; _y2= y2; } public override void draw () { drawLine(_x1, _y1, _x2, _y1); drawLine(_x2, _y1, _x2, _y2); drawLine(_x2, _y2, _x2, _y1); drawLine(_x2, _y1, _x1, _y1); } }
C#
// With abstract base class abstract class Shape { private Drawing _dp; Shape (Drawing dp) { _dp= dp; } abstract void draw (); protected void drawLine ( double x1, double y1, double x2, double y2) { _dp.drawLine( x1, y1, x2, y2);} protected void drawArc ( double x, double y, double radius, double fromAngle, double toAngle){ _dp.drawArc( x,y,radius, fromAngle, toAngle); } }
Page 83
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
161# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Example#Con8nued#
class V2Drawing : Drawing { public override void drawLine (double x1,double y1, double x2, double y2){ DP2.drawline( x1, x2, y1, y2);} public override void drawArc ( double x, double y, double radius, double fromAngle, double toAngle) { DP2.drawarc(radius, x, y, fromAngle, toAngle); } } class DP1 { static void draw_a_line ( double x1, double y1, double x2, double y2) { // draw_a_line implementation given to us} static void draw_an_arc( double x, double y, double radius, double from_angle, double to_angle) {
// draw_an_arc implementation given to us } } class DP2 { static void drawline ( double x1, double y1, double x2, double y2) { // drawline implementation given to us } static void drawarc( double radius, double x, double y, double fromangle, double toangle) { // drawarc implementation given to us } }
C#
162# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Example#Implementa8on##class Client { public static void main (String argv[]) { Shape s1; Shape s2; Drawing dp; // See comments below to see // what gets returned dp= Factory.getDP(); s1= Factory.getShape(dp); dp= Factory.getDP(); s2= Factory.getShape(dp); s1.draw(); s2.draw(); }} // Factory: // 1st call: getDP returns V1Drawing // 1st call: getShape returns // new Rectangle(dp,1,1,2,2); // 2nd call: getDP returns V2Drawing // 2nd call: getShape returns // new Circle( dp,2,2,4);
interface class Shape { void draw (); }
class Rectangle implements Shape{ private Drawing _dp; Rectangle (Drawing dp, double x1, double y1, double x2, double y2) { _dp = dp; _x1= x1; _y1= y1;
_x2= x2; _y2= y2;} public void draw () { _dp.drawLine(_x1,_y1,_x2,_y1); _dp.drawLine(_x2,_y1,_x2,_y2); _dp.drawLine(_x2,_y2,_x2,_y1); _dp.drawLine(_x2,_y1,_x1,_y1); } }
Java
Page 84
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
163# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Example#Con8nued#interface Drawing { void drawLine ( double x1, double y1, double x2, double y2); void drawArc(double x, double y, double radius, double fromAngle,double toAngle);} class V1Drawing implements Drawing { public void drawLine ( double x1, double y1, double x2, double y2) { DP1.draw_a_line(x1,y1,x2,y2); } public void drawArc ( double x,double y,double radius, double fromAngle, double toAngle){ DP1.draw_an_arc( x, y,radius, fromAngle, toAngle); } }
Java
class Circle implements Shape { private Drawing _dp; Circle (Drawing dp, double x, double y, double radius) {
_dp = dp; _x= x; _y= y;
_radius= radius; } public void draw () { _dp.drawArc(_x,_y,_radius, 0, 360); } }
164# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Example#Implementa8on##With#Abstract#
// with abstract class abstract class Shape { private Drawing _dp; Shape (Drawing dp) { _dp= dp; } abstract void draw (); protected void drawLine ( double x1, double y1, double x2, double y2) { _dp.drawLine( x1, y1, x2,
y2); } protected void drawArc ( double x, double y, double radius, double
fromAngle, double toAngle){ _dp.drawArc( x, y,
radius, fromAngle, toAngle); } }
Java
class Rectangle extends Shape { Rectangle (Drawing dp, double x1, double y1, double x2, double y2) { super( dp); _x1= x1; _y1= y1; _x2= x2; _y2= y2; } public void draw () { drawLine(_x1, _y1, _x2, _y1); drawLine(_x2, _y1, _x2, _y2); drawLine(_x2, _y2, _x2, _y1); drawLine(_x2, _y1, _x1, _y1); } } class Circle extends Shape { Circle (Drawing dp, double x, double y, double radius) { super( dp); _x= x; _y= y; _radius= radius; } public void draw () { drawArc(_x,_y,_radius, 0, 360); } }
Page 85
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
165# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Example#Con8nued#
class V2Drawing implements Drawing { public void drawLine ( double x1, double y1, double x2, double y2) { DP2.drawline( x1, x2, y1, y2);} public void drawArc ( double x, double y, double radius, double fromAngle, double toAngle) { DP2.drawarc(radius, x, y, fromAngle, toAngle); } }
class DP1 { static void draw_a_line ( double x1, double y1, double x2, double
y2) { // draw_a_line implementation given to us } static void draw_an_arc( double x, double y, double radius, double from_angle, double to_angle) {
// draw_an_arc implementation given to us } } class DP2 { static void drawline ( double x1, double y1, double x2, double y2) { // drawline implementation given to us } static void drawarc( double radius, double x, double y, double fromangle, double toangle) { // drawarc implementation given to us } }
Java
166# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Example#Implementa8on#
void main (String argv[], int arc) { Shape *s1; Shape *s2; Drawing *dp; dp= Factory::getDP(); s1= Factory::getShape(dp); dp= Factory::getDP(); s2= Factory::getShape(dp); s1->draw(); s2->draw(); } NOTE: Memory management has not been tested and the INCLUDE statements are not being shown.
class Shape { public: Shape (Drawing *dp); virtual void draw(); protected: drawLine( double x1, double y1, double x2, double y2); drawArc( double x, double y, double rad, double fromAngle, double toAngle); private: Drawing *_dp; }; Shape::Shape (Drawing *dp) { _dp= dp; } void Shape::drawLine( double x1, double y1, double x2, double y2) { _dp->drawLine( x1, y1, x2, y2); } void Shape::drawArc( double x, double y, double radius, double fromAngle, double toAngle){ _dp->drawArc( x, y, radius, fromAngle, toAngle); } !!
C++
Page 86
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
167# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Example#Con8nued#
class Rectangle : public Shape { public: Rectangle (Drawing *dp, double x1, double y1, double x2, double y2); private: double _x1, _y1, _x2, _y2; }; Rectangle::Rectangle (Drawing *dp, double x1, double y1, double x2, double y2) : Shape(dp) { _x1=x1; _y1=y1; _x2=x2; _y2=y2; } void Rectangle::draw () { drawLine(_x1, _y1, _x2, _y1; drawLine(_x2, _y1, _x2, _y2); drawLine(_x2, _y2, _x2, _y1); drawLine(_x2, _y1, _x1, _y1); }
class Circle : public Shape { public: Circle ( Drawing *dp, double x, double y,
double radius); private:
double _x, _y, _radius;
}; Circle::Circle (Drawing *dp, double x, double y,
double radius) : Shape(dp) { _x= x; _y= y; _radius= radius; }
void Circle::draw () { Shape::drawArc( _x,_y,_radius,0,360);
}
C++
168# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Example#Con8nued#
###
class V2Drawing : public Drawing { public: void drawLine ( double x1, double y1,
double x2, double y2); void drawArc ( double x, double y, double radius, double fromAngle,
double toAngle); }; void V2Drawing::drawLine ( double x1,double y1,
double x2,double y2){ DP2::drawline( x1, x2, y1, y2); }
void V2Drawing::drawArc ( double x,double y, double radius, double fromAngle, double toAngle){ DP2::drawarc( radius, x, y, fromAngle, toAngle); }
class V1Drawing : public Drawing { public: void drawLine ( double x1, double y1, double x2, double y2);
void drawArc ( double x1, double y1, double radius, double fromAngle,
double toAngle); }; void V1Drawing::drawLine (double x1, double y1, double x2, double y2) {
DP1::draw_a_line( x1, y1, x2, y2); } void V1Drawing::drawArc ( double x, double y, double radius, double fromAngle, double toAngle){ DP1::draw_an_arc(x,y,radius, fromAngle, toAngle);
}
C++
class Drawing { public: virtual void drawLine (double x1,double y1, double x2,double y2) =0; virtual void drawArc (double x1, double y1, double radius, double fromAngle,
double toAngle)=0; };
Page 87
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
169# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Example#Con8nued#
class DP1 { public: static void draw_a_line ( double x1, double y1, double x2, double y2); static void draw_an_arc( double x, double y, double radius, double fromAngle, double toAngle); }; class DP2 { public: static void drawline ( double x1, double x2, double y1, double y2); static void drawarc ( double radius, double x, double y, double fromAngle, double toAngle); }; // Implementations given to us
C++
170# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Where#is#varia8on#coming?#
Drawing Program/ Shape
DP1 DP2
Line
Rectangle
Circle
Page 88
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
171# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Look#For#Abstrac8ons#
! Commonali8es#could#be##– Func8ons#– Data##
! Alterna8ve#interfaces#may#produce#different#design##
! Example#on#next#slide##
172# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Drawing#Another#Way#
Line#
DrawingPrimi8ve##
Arc#
Shape#
DrawingPrimi8ve[]#getPrimi8ves();##
In#DrawingProgram:####
draw(Shape#s)#{#
##DrawingPrimi8ve#[]#dp#=#s.getDrawingPrimi8ves();##
##//#Now#draw#each#one##
##}#
#
What#are#advantages#/#disadvantages?#
Page 89
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
173# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Drawing#Another#Way#(2)#
interface Shape { DrawingPrimitive [] getPrimitives(); } class Rectangle implements Shape { double x1; double y1; double x2; double y2; DrawingPrimitive [] getPrimitives() {
DrawingPrimitive [] dp = { new Line(x1,y1,x1,y2), new Line(x1,y1,x2,y1), new Line(x2,y1,x2,y2), new Line(x1,y2,x2,y2)}
return dp; }
174# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Drawing#Another#Way#–#One#Class##(3)#
class Shape { Shape (DrawingPrimitive [] primitives)
{ this.primitives = primitives;
} DrawingPrimitive [] primitives; DrawingPrimitive [] getPrimitives() { return primitives }; } // Each object has its own primitives Shape rectangle({ new Line(x1,y1,x1,y2), new Line(x1,y1,x2,y1), new Line(x2,y1,x2,y2), new Line(x1,y2,x2,y2)});
Page 90
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
175# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
How#Drawing#Usually#Works#(op8onal)#
Drawing#(Graphics#Device#Interface)#draws#specific#shapes#(not#derived#from#a#Shape)##
interface GDI { drawRectangle(Rectangle r) drawCircle(Circle c) drawLine(Line l) drawPolyline(Line [ ] lines ) }
class Screen implements GDI //What are advantages / disadvantages?
176# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Who’s#In#Charge?##
! Class#PhoneNumber#– Dial#(Phone)#
! Class#Phone#– Dial(PhoneNumber)#
#
Page 91
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
177# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Who’s#In#Charge#(2)?##
! One#more#thing#to#dial:###
! Class#AccountNumber#– Dial#(Phone)#
! Class#Phone#– Dial(PhoneNumber)#
– Dial(AccountNumber)##
#178# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Who’s#In#Charge#(3)#?#
! Interface#Dialable##– DialableString#getStringToDial();#
! Class#AccountNumber#implements#Dialable#{##DialableString#getStringToDial()#{##//..##}###}#
! Class#PhoneNumber#implements#Dialable##
! Class#Phone#– Dial(Dialable)#
#
#
Page 92
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
179# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Canonical#Bridge#PaWern#
Concrete1ImpA
+ opImp1()+ opImp2()
ImpB+ opImp1()+ opImp2()
Abstraction+ operation()
Implementation+ opImp1()+ opImp2()
operat ion() { imp.opImp1()}
Concrete2
operation() { imp.opImp2()}
180# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Bridge#PaWern#as#an#Example##of#the#GoF#Approach#
Concrete1ImpA
+ opImp1()+ opImp2()
ImpB+ opImp1()+ opImp2()
Abstraction+ operation()
Implementation+ opImp1()+ opImp2()
operat ion() { imp.opImp1()}
Concrete2
operation() { imp.opImp2()}
(1)'(2)'encapsulates'variaAon'
(3)'
(1)'
(1) Find0what0varies0(the0abstrac+ons0and00implementa+ons)0and##(2) Encapsulate0it.0(3) Favor00object0delega+on0over0classIinheritance0#
(2)'encapsulates'variaAon'
Page 93
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
181# ### #16#October#2013#
The'Adapter'Pa*ern'
182# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
The#Adapter#PaWern#
! Issue:#– Class#has#right#stuff##
! But#wrong#interface#! GoF#Intent:#
– #Convert#class#interface#into#the#one#client#expects##– #Allows#classes#with#incompa8ble#interfaces#to#work#together#
*Design%Pa2erns,%Elements%of%Reusable%Object<Oriented%So?ware,#Gamma,#Helm,#Johnson,#Vlissides#
Paradigm00PaKerns0Wisdom0
Principles0 Prac+ces0
Quali+es##
Page 94
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
183# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Our#Problem#
Shape + setLocation() + getLocation() + display() + fill() + setColor() + undisplay()
Point + display() + fill() + undisplay()
Line + display() + fill() + undisplay()
Square + display() + fill() + undisplay()
184# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
What#We#Have#
XX_Circle
+ set_location() + get_location() + display_it() + fill_it() + set_its_color() + undisplay_it()
Page 95
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
185# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
What#We#Want#
! Want#XX_Circle#to#behave#like#a#Shape#– No#polymorphism#with#XX_Circle:#
! Author#of#XX_Circle#not#willing#or#able#to#change#XX_Circle’s#interface#
Shape
XX_CIRCLE
=
186# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
How#to#Implement#the#PaWern#
Shape + setLocation() + getLocation() + display() + fill() + setColor() + undisplay()
Point + display() + fill() + undisplay()
Line + display() + fill() + undisplay()
Square + display() + fill() + undisplay()
XX_Circle + set_location() + get_location() + display_it() + fill_it() + set_its_color() + undisplay_it()
Circle + display() + fill() + getLocation() + setLocation() + setColor() + undisplay()
Page 96
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
187# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Example#
class Circle : Shape { … private XX_circle pxc; … public Circle () { pxc= new XX_circle(); } public void override display() { pxc.display_it(); } }
C#
188# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Example#
class Circle extends Shape { … private XX_circle pxc; … public Circle () { pxc= new XX_circle(); } public void display() { pxc.display_it(); } }
Java
Page 97
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
189# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Example#
IN HEADER class Circle : public Shape { private: XX_circle *pxc; } IN CONSTRUCTOR instantiate and initialize XX_circle. Have it refer to pxc IN CODE void Circle::display () { pxc->display_it(); }
C++
190# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Adap8ng#
// May have some state to keep class Circle implements Shape { private XX_circle pxc; private Color color; setColor(Color c)
{ this.color = c; }
fill() { pxc.fill_it(color):; }
}
Page 98
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
191# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
General#Approach#
! Client#works#with#other#classes#without#"knowing"#which#one#– Create#an#interface#– Adapt#each#class#to#implement#that#interface#
! Adap8ng##is#also#called#"wrapping"#
192# ### #16#October#2013#
The'Façade'
Page 99
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
193# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
The#Façade#PaWern#
! Want#:#– To#use#a#subDset#of#a#complex#system#
– Or#to#provide#OO#access#to#a#nonDOO#system#
! GoF#Intent*:##– Provide#a#unified#interface#to#a#set#of#interfaces#in#a#subsystem##
– Facade#defines#a#higherDlevel#interface#that#makes#the#subsystem#easier#to#use#
*Design%Pa2erns,%Elements%of%Reusable%Object<Oriented%So?ware,#Gamma,#Helm,#Johnson,#Vlissides#
Paradigm00PaKerns0Wisdom0
Principles0 Prac+ces0
Quali+es##
194# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Using#a#Complex#System#
! If#your#group#had#to#use#parts#of#a#complex#system,#would#you:#A. Have#everyone#learn#how#to#use#it?#B. Have#one#person#create#an#interface#to#use?#
! If#you#picked#B,#what#that#person#created#would#be#a#Façade#
Page 100
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
195# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Insula8ng#Ourselves#From#the#Complex#System#
Façade
#
196# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Façade#Example#(1)#
! #Example#StoreStringInFile(String filename, String data); // calls open, write, close String RetrieveStringFromFile(String filename); // calls open, read, close
! Error#handling#(try,#catch,#etc.)#in#the#implementa8on#code#! Allows#easy#mock##
– Read/write#to#memory,#rather#than#a#file##
#
Page 101
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
197# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Façade#Example#(2)#
SimpleFileStorageFacade#####SelectStorageDirectory(String#directory)######StoreStringInFile(String#filename,#String#data)#:#boolean#####RetrieveStringfromFile(String#filename)#:#String#
File#//#Read,#write,#open,#close#//#Excep8on#handling##
Directory#//#change#working#directory#
SimpleFileStorageFacadeMock####SelectStorageDirectory(String#directory)#####StoreStringInFile(String#filename,#String#data)#:#boolean#
#//#stores#in#memory#–#maybe#a#map#?#####RetrieveStringfromFile(String#filename)#:#String#
#//#retrieves#from#memory##
LiWle#more#complete#
198# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Standard#Façade#vs.#Encapsula8ng#Facade#
! Standard#Façade#provides#interface#– Clients#may#use#underlying#
system#directly#
! Encapsula8ng#Façade#restricts#access#to#the#underlying#system##– Clients#must#use#Façade#
Page 102
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
199# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Comparing#Façade#With#Adapter#
Client Pre-Existing?which pattern?
Façade# Adapter#Pre5ExisAng,'or'Foreign'classes?'
Yes# Yes#
Is'there'an'exisAng'interface'we'must'adhere'to?'
No# Yes#
Are'we'trying'to'enable'polymorphism?'
No# Usually#
Are'we'creaAng'a'new'interface'for'simplificaAon?'
Yes# No#
Is'statefullness'a'concern?' Yes,#Façades#tend#to#be#large#
Not#usually#
200# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Adapter#and#Façade#
! Use##Adapter#and#Façade#– Defer#Worrying#About#Your#Interface#
– Make#interfaces#of#classes#to#be#the#way#you#want#
! Design#by#context#– #First#figure#out#what#you#want##– Then#adapt#(or#simplify#with#a#Facade)#the#interface#to#that#
Page 103
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
201# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Microso_#Founda8on#Classes#(MFC)#Façade##
MFC#Classes#####Window#####Dialog##
Windows#SDK#####Win#98##
Windows#SDK#####Windows#7##
Windows#SDK#####Windows#2000#
Applica8on#
Note:#NonDencapsula8ng#facade#
202# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Façade###Usage##
Your#system#
Façade##
Third#party#library##
Page 104
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
203# ### #16#October#2013#
The'Abstract'Factory'
204# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Strategy#Revisited#
! Abstract#Factory#is#strategy#of#strategies##! Here’s#an#example#
Page 105
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
205# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Switch#to#Strategy(1)#
// Just a switch, not a strategy enum Country {USA, MEXICO, CHINA}; functionOne (Country c){ switch(c) { case USA: doOneUSA(); break; case MEXICO: doOneMexico(); break; case CHINA: doOneChina(); break; } };
Switch#in#one#func8on#
206# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Switch#to#Strategy#(2)#
//FACTORY Strategy getStrategy(Country c){ switch(c) case USA: return new USAStrategy(); case MEXICO: return new MexicoStrategy(); case CHINA: return new ChinaStrategy(); break; } }; // USAGE: void functionOne (Country c){ Strategy s = getStrategy(c); s.doFunctionOne();}
interface Strategy { void doFunctionOne(); }; class USAStrategy implements Strategy { void doFunctionOne() { doOneUSA(); }}; class MexicoStrategy implements Strategy { void doFunctionOne(){ doOneMexcio(); } }; // .. And so on
To#a#strategy#
Page 106
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
207# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Switch#to#Strategy#(3)#
functionTwo (Country c){ switch(c) { case USA: doTwoUSA(); break; case MEXICO: doTwoMexico(); break; case CHINA: doTwoChina(); break; } };
Now#a#2nd#switch##
208# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
How#to#organize#?#
County/ Function
USA
MEXICO
FunctionOne
FunctionTwo
FunctionThree
Page 107
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
209# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Switch#to#Strategy#(4)#
class MexicoStrategy implements Strategy { void doFunctionOne() { doOneMexcio(); } void doFunctionTwo() { doTwoMexcio(); } }; // .. And so on void functionTwo (Country c){ Strategy s = getStrategy(c); s.doFunctionTwo();}
interface Strategy { void doFunctionOne(); void doFunctionTwo(); }; class USAStrategy implements Strategy { doFunctionOne() { doOneUSA(); } doFunctionTwo() { doTwoUSA(); };
Add#to#strategy#
210# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Switch#to#Strategy#(5)#
interface Strategy { void doFunctionOne(); void doFunctionTwo(); //…. void doFunctionNintyNine(); }; class USAStrategy implements Strategy { void doFunctionOne() { doOneUSA(); } void doFunctionTwo() { doTwoUSA(); }; //…. void doFunctionNinetyNine() {
Now#99##func8ons##added#to#strategy#
Page 108
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
211# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Switch#to#Strategy#(5)#
interface StrategyFactory { StrategyA getStrategyA(); StrategyB getStrategyB(); ///… StrategyZ getStrategyZ(); }; class USAStrategyFactory() implements StrategyFactory { StrategyA getStrategyA() { return new USAStrategyA(); } StragegyB getStrategyB(){ return new USAStrategyB(); } //.. And so forth };
interface StrategyA { { // Related functions void doFunctionOne(); void doFunctionTwelve(); }; class USAStrategyA implements StrategyA { void doFunctionOne() { doOneUSA(); } void doFunctionTwelve() { doTwelveUSA(); } };
Break#into#related#strategies#
212# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Switch#to#Strategy#(6)#
StragetyFactory getInstanceStrategyFactory(Country c){ switch(c) { case USA: new USAStrategyFactory( (); break; case MEXICO: new MexicoStrategyFactory( (); break; case CHINA: new ChinaStrategyFactory( (); break; } };
Now#get#the#strategy#factory#
Page 109
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
213# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Switch#to#Strategy#(7)#
void functionTwelve(Country c) { StrategyFactory sf = getInstanceStrategyFactory(c); StrategyA sa = sf.getStrategyA(); sa.doFunctionTwelve(); } // Instead of previous operation void functionTwelve(Country c){ Strategy s = getStrategy(c); s.doFunctionTwelve();}
Usage:#
214# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
The#Abstract#Factory#PaWern#
! GoF#Intent:##– Need#to#create#families#of#objects#for#par8cular#situa8ons.##
– Provide#interface#for#crea8ng#families#of#related#or#dependent#objects##! Without#specifying#their#concrete#classes#
Design0PaKerns:0Elements0of0Reusable0ObjectIOriented0SoLware#by#Gamma,#Helm,#Johnson,#Vlissides.#AddisonDWesley#Professional.#1995.#
Page 110
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
215# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Abstract#Factory:#Contextual#Forces#
! Mo8va8on:##– Instan8ate#families#of#objects#
! Encapsula8on:##– Number#of#cases#
– Concrete#types#of#all#services#– Issue#that#case#varies##
216# ### #16#October#2013#
Not'an'Ending,'But'a'Beginning'
Page 111
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
217# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Purpose#of#this#Course#(Revisited)#
! Present#a#powerful#way#of#designing#applica8on#architectures#! Incorporates:#
– Code#Quali8es##– Design#PaWerns#– CommonalityDVariability#Analysis#– Contextual#Design#(a#la#Alexander)#
218# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Summary#
! Design#in#context##! Code#quali8es##as#basis#for#paWerns##! Favor#delega8on#over#inheritance#! Encapsulate#variability#! What#else?##
Page 112
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
219# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Thank#You##
Please#Fill#Out#Evalua8ons#
info@netobjec+ves.com000www.netobjec+ves.com0
220# #Copyright#©#2008#Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Supplemental'
Page 113
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
221# ### #16#October#2013#
Factories'
Paradigm00PaKerns0
Wisdom0Principles0 Prac+ces0
Quali+es##
222# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Another#Issue#of#Perspec8ve#
! PaWerns,#e.g.#strategy,#bridge##– Create#context#for#factory##
! Factories##– Only#construct#objects,#do#not#use#
objects#Shape +centerX:int +centerY:int
Circle +diameter:int
Square +width:int +height:int
Factory +make():Shape
Client
~2
Page 114
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
223# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
The#Use#of#Factories#
! Factories#decouple#object#being#used#from#client##! Factories#promote#encapsula8on#of#design#
– 1st##Determine#interfaces#and#interac8ons#of#objects##! Conceptual#and#specifica8on#perspec8ves#
– 2nd##Get#right#objects#with#factory#! Implementa8on#perspec8ve##
224# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
How#do#Factories#Make#Decisions?#
! "Extrinsic"#(to#the#client)#– Example:#
! Configura8on#file#or#device#iden8fica8on#(e.g.#version#of#Windows)#
– Only#factory#couples#to#configura8on#file##! "Intrinsic"#(to#the#client)##
– Client#decides#and#passes#a#parameter##
! "Rule#Based“#– Based#on#a#rule#– Example##
! If#user#is#administrator,#create#object#with#write#privileges##
– Only#factory#couples#to#rule##
Page 115
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
225# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
#Factory#Example##
// Client Selection enum EncryptionType {Strong, Weak, None}; Encryptor getEncryptorInstance(EncryptionType et)
{ switch(et) { case Strong: return new E128(); case Weak: return new E64(); case None: return new E0(); default: throw new Exception( “Look at the EncryptionType”); } }
226# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
#Factory#Alterna8ves#
enum EncryptionType {Strong, Weak, None}; // Table (struct, array, etc.)
Type Class Strong E128 Weak E64 None E0
Encryptor getEncryptorInstance(EncryptionType et) { for (i = 0; i < table.size; i++) { if (et == table[i].type) // return new object of table[i].class
} throw new Exception(“Look at the EncryptionType”); }
// Or array indexed by enum Encrypt [] encrypt= {new E128(), new E64(), new E0()}; return encrypt[et];
Page 116
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
227# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Factory#Alterna8ve#D#Service#Locator#PaWern#
class Chip { private Encryptor myEncryptor; Chip () {
myEncryptor = ServiceLocator.getEncryptor(); } } // Service locator checks a configuration file for type of encryptor to return
228# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Concept#/#Varia8ons#
Encryption
E128
E64
E0
Send
TCP
FTP
UDP
Page 117
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
229# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Factory#For#Two#Strategies#
enum ChipType {ForCommercial, ForUS, ForImportantCustomer}; Chip getChip(ChipType ct) {
switch (ct) { case ForCommercial:
return new Chip(GetEncryptorInstance(Weak), GetSendInstance(TCP));
case ForUS: return new Chip(GetEncryptorInstance(Strong), GetSendInstance(FTP));
case ForImportantCustomer: return new Chip(GetEncryptorInstance(Weak), GetSendInstance(FTP);
}} // Or use table
230# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
#Discussion#Exercise#
! You#have#exis8ng#Account#object#– You#need#to#log#all#access#to#its#
public#methods#! But#only#for#certain#accounts#and/or#at#certain#8mes#of#the#day#
– You#don’t#want#client#code#to#change#a#lot##! (or#at#all,#if#possible)#
! What#would#you#do?#
Please#Don’t#Turn#the#Page#Un8l#Instructed#to#Do#So#
~2
Account + Account(AccountID id) + AddMoney(Dollar d) + TakeOutMoney(Dollar d)
Page 118
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
231# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Workspace#
232# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Workspace#
Page 119
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
233# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Workspace#
234# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Workspace#
Page 120
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
235# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
One#Approach:#An#Intervening#Class#
Client Logger Account
Writes to a log file, then delegates
~2 236# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Account#Logger#(Proxy)##
Account
+ addMoney() + takeOutMoney()
Account_Impl LoggingAccount
Client
Call#logger#before#calling#original#method##
.
+ addMoney() + takeOutMoney()
+ addMoney() + takeOutMoney()
Page 121
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
237# ### #16#October#2013#
The'Family'of'Proxy'Pa*erns'
Paradigm00PaKerns0Wisdom0
Principles0 Prac+ces0
Quali+es##
238# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
The#Proxy#PaWern#
! Issue:#– Need#to#add#func8onality#before#or#a_er#accessing#an#object#
! Client#should#not#know#it#is#talking#to#a#different#object#! GoF#Intent:##
– Provide#a#surrogate#or#placeholder#for#another#object*#! Summary:#
– Proxy#acts#on#behalf#of#another#class#– Proxy’s#interface#must#be#same#as#class#it#is#duplica8ng#
*Design%Pa2erns,%Elements%of%Reusable%Object<Oriented%So?ware,#Gamma,#Helm,#Johnson,#Vlissides#
Page 122
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
239# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
The#Proxy#PaWern#
! Many#uses#for#proxy#paWern#! Some#are:#
– Access#protec8on#! Protec+on0proxy#provides#security#for#another#object#
– Caching#! Cache0proxy#provides#caching#for#accessing#another#object#
– Virtualiza8on#! Virtual0proxy##provides#holding#point#for#another#object##
240# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
The#Protec8on#Proxy#PaWern#
! Need#to#control#access#to#exis8ng#object##! Don’t#want#to#change#exis8ng#data#object##
– Or#how#it#is#referred#to##! Follows#openDclosed#principle#
– Closed#=#exis8ng#object##– Open#=#adding#access#control#
Page 123
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
241# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
The#Protec8on#Proxy#PaWern#
! Example:#– Teachers#place#test#problems#and#answers#in#database#
! Access#through#Problem#with:#– String#getQues8on#(int#problem_number)#D#returns#ques8on#as#string#– String#getAnswer#(int#problem_number)#D#returns#answer#as#string#
! Now#give#students#access#to#the#ques8on#– But#not#the#answers#
! User#class#has#method#– Boolean#isTeacher()#–#returns#if#User#is#teacher##
242# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Possible#Solu8ons#
! Could#add#isTeacher()#call#before#every#getAnswer()#call#– Problem:##
! #Have#to#change#Client#code#wherever#getAnswer()#is#used##! Make#Problem#class#smarter#
– Add#isTeacher()#to#getAnswer#(int#problem_number)##– Problems:#
! Breaks#open/closed#! May#have#side#effects#for#other#Client#using#Problem##
Page 124
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
243# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Protec8on#Proxy#Solu8on#
! Create#a#Problem#interface#– Both#original#Problem#and#a#new#class#(SecurityProblem)#implement#it#
! SecurityProblem#checks#user#before#passing#back#answers#– Uses#Problem#to#do#real#work#
! Client#gets#SecurityProblem,#not#Problem#to#use##– Can’t#tell#the#difference#
244# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Protec8on#Proxy#Looks#Like#
Problem
+ getAnswer() + getQuestion()
Problem_Impl
+ getAnswer() + getQuestion()
SecurityProblem
+ getAnswer() + getQuestion()
Client
getAnswer checkis type of client calls Problem_Impl's getAnswer. getQuestion just calls Problem_Impl's getQuestion.
Page 125
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
245# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Protec8on#Proxy##
class SecurityProblem implements Problem { Problem original; SecurityProblem() { original = new Problem_Impl(); } String getQuestion(int which) { return original.getQuestion(which); } String getAnswer(int which) { if (User.isTeacher()) return original.getAnswer(which); else return “I can't give you answer”; } // Could also have SecurityProblem(Problem p); }
246# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
How#It#Works# : Client : Security
Problem : Problem _Impl Problem
_Factory
2: Instantiate
5: Request question 6: Request question 7: Return question
8: Return question 9: Request answer
10: Do I have a teacher? 11: If no, say can't give you answers
12: If yes, ask for answer 13: Return answer
14: Return answer
1: Get Problem
3: Instantiate (pass in Problem_Impl) 4: Return Object
Page 126
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
247# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Common#Characteris8cs#of#All#Proxies#
! Proxy#paWern#characteris8cs:#– Client#uses#proxy#class#instead#of#original#class#– Proxy#and#original#class#have#same#interface##
– Proxy#calls#original#class#for#services#! No#duplica8on#of#func8onality#
248# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
The#Proxy#PaWern#Generalized:#Class#Diagram#
Original + Request()
Proxy + Request()
Interface + Request()
Client
Request() calls Original’s Request()
Page 127
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
249# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
The#Proxy#PaWern#Generalized:#Interac8ve#Diagram#
Client Proxy Original
1: Request
2 : do necessary pre-processing
3: request
5: do necessary post-processing
6: Respond to client
4: respond to request
250# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
The#Cache#Proxy#PaWern#Example#
! Needs:#– Improve#performance#in#accessing#data#
– No#change#in#exis8ng#object#! Example#Situa8on:##
– Applica8on#makes#read0only0use#of#sta8c#data#through#Table#class#! Table#data#resides#on#disk#
! Problem:#– Performance#is#slow#– Many#accesses#to#table#are#for#the#same#data##
Page 128
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
251# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Cache#Proxy#Looks#Like#
Cache_Table
+ read_data()
Table
+ read_data()
Table_Impl
+ read_data()
Client
read_data() calls Table_Impl read data() if info isn't cached
252# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
The#Virtual#Proxy#PaWern#Example#
! Needs:#– Exis8ng#object#uses#many#system#resources##
– Client#doesn’t#reference#object#immediately#! Don’t#want#to#use#system#resources#un8l#necessary#
! Need#a#placeholder#for#it#! Example:##
– Applica8on#contains#many#graphic#images#! Only#shows#a#few#of#them#at#a#8me#
! Problem:##– If#all#of#the#images#instan8ated,#run#out#of#memory##
Page 129
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
253# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Virtual#Proxy#Looks#Like#
Image
+ display()
Image_Impl
+ display()
VirtualImage
+ display()
Client
display is implemented by instantiating the corresponding Image and displaying
- filename
254# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
The#Remote#Proxy#PaWern#
! Remote#proxy##– Access#object#on#remote#machine#
– Local#proxy#looks#like#that#object##! Almost#transparent#
– Client#may#have#to#deal#with#network#unavailability#issues#
Local#Proxy# Remote#Object#
Client# Server#Somewhere#
Page 130
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
255# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Other#Proxies#
! Smart'reference'proxy*.#– Replaces#“bare”#reference##– Adds#func8onality,#for#example:#
! Counts#number#of#references##
! SynchronizaAon'proxy*#– Coordinates#mul8ple#simultaneous#accesses#to#a#component#
– Locks/unlocks#the#object# ##
! Firewall'proxy*.##– Protects#local#clients#from#the#outside#world##
*Pa2ern<Oriented%So?ware%Architecture,#Buschmann,#et.#al.##256# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Browser#Proxy##
Browser## Remote#Web#Server##
Proxy##
Page 131
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
257# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
What#the#Proxy#Teaches#Us#
! Use#interfaces#for#objects#whose#behavior#or#use#may#change#
! Proxies###– Accommodate#changes#that#require#preD#and#postDprocessing#
– Separate#op8onal#behavior#from#"always“#behavior###! Thus,#improved#cohesion#
258# ### #16#October#2013#
The'Decorator'Pa*ern'
Paradigm00PaKerns0Wisdom0
Principles0 Prac+ces0
Quali+es##
Page 132
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
259# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
The#Decorator#PaWern#
Mo8va8on#– Change#func8onality#of#an#object#of#a#class#
! Rather#than#the#en8re#class#– Dynamically#add#addi8onal#func8onality#– Pick#from#addi8onal#behaviors#
! Add#desired#ones#for#a#par8cular#case#! Analogy#
– Electrical#connectors##! One#with#on/off#"#One#with#fuse#"#One#with#UPS##
! GoF#Intent:##– AWach#addi8onal#responsibili8es#to#an#object#dynamically.##
*Design%Pa2erns,%Elements%of%Reusable%Object<Oriented%So?ware,#Gamma,#Helm,#Johnson,#Vlissides#
260# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Decorator#PaWern#for#Streaming#IO#
Client
TCPIPStream + flush()
FileStream + flush()
U128 + flush()
CompressStream + flush()
Stream + output() + flush()
StreamDecorator
Page 133
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
261# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Encapsula8on#
FileStream#
Compress#
U128#
Client#
Convert#to#U128#and#then#flush#
Compress#and#then#flush#
Send#
Each#circle#encapsulates#(hides)#what#is#within#from#what#is#without.###
Each#en8ty#(U128,#Compress,#FileStream)#also#does#not#know#if#it’s#the#outer#circle#or#not#
Construc8on:###Stream#s#=#new#U128(#####new#Compress#(#######new#FileStream(“name”)));#Use:####s.output();####s.flush();##
262# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Comparing#Adapter,#Façade,#Proxy#and#Decorator#
Adapter Facade Proxy Deco-rator
Have pre-existing stuff? Yes Yes Yes Yes Is the client expecting a particular interface?
Yes No Yes Yes
Want to make a new interface to simplify things?
No Yes No No
Modifying interface to what clients expect?
Yes No No No
Want some new function before or after the normal action?
Maybe, but not intent
Maybe, but not intent
Yes (sta-
tically)
Yes (dyna-
mically)
Client Pre-Existing?which pattern?
Page 134
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
263# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Object#Diagram#of#Decorator#/#Proxy#
Decorator''B'
Decorator'A'
Client'
Original'
Proxy'
Client'
Original'
Decorator' Proxy' ! Proxy##– Func8onality#usually#added#sta8cally##
– Usually#knows#original#object#
! Decorator#– Func8onality#usually#added#dynamically##
– Does#not#know#original#object##
264# ### #16#October#2013#
Chain'of'Responsibility'
Paradigm00PaKerns0Wisdom0
Principles0 Prac+ces0
Quali+es##
Page 135
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
265# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
The#Chain#of#Responsibility#PaWern#
! Issue:#– Any#of#a#set#of#objects#can#perform#a#task#– Requestor#of#task#does#not#want#to#know#which#one#does#it#
! GoF#Intent:##– Decouple#sender#of#a#request#to#its#receiver##
! By#giving#more#than#one#object#a#chance#to#handle#the#request#
– Chain#receiving#objects#! Request#passed#along#the#chain#un8l#an#object#handles#it*##
! Example:#Have#a#message#to#decode#– Chain#decoders#together#– Pass#message#to#each#one#un8l#one#decodes#it#
*Design%Pa2erns,%Elements%of%Reusable%Object<Oriented%So?ware,#Gamma,#Helm,#Johnson,#Vlissides#
266# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Chain#of#Responsibility#Object#Diagram##
Decoder1
Decoder3
Decoder2
Decoder4
return computedvalue or given
return computedvalue or given
return computedvalue or given
return computedvalue or given
2: decode ifpossible
1: decode ifpossible
3: decode ifpossible
4: decode ifpossibleClient
Requestto decode
Page 136
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
267# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Example#CoR#Diagrammed#
Client
Decoder1 + decode()
Decoder2 + decode()
Decoder3 + decode()
Decoder + decode()
1#
0..1#
268# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Who#Knows#How#to#Build#the#Chain?#
! Have#to#decide#somewhere:#– Which#decoders#belong#in#the#chain#– What#order#they#should#be#in#– How#the#Chain#will#end##
! Request%execuBon%not%guaranteed%– Possible#it#not#handled#at#all#
! Good#to#have#default#"always"#en8ty#at#end#of#chain#– Either#default#behavior#or#error#signaling##
! Op8ons#included:#– Hard#code#chain#in#Client#– Client#gets#chain#from#factory##
! Factories##usually#less#likely#to#grow#in#number#than#clients#
Page 137
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
269# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Code#Example#of#Chain#of#Responsibility#
class Client { public string Decode( string message, Decoder aDecoder) { return aDecoder.Decode( message); } } abstract class Decoder {
private Decoder trailer; public Decoder ( Decoder nextDecoder) { trailer= nextDecoder; } public string Decode ( string message) { if (MyAction(message))
return DecodeString( message); if (trailer!= null) return trailer.Decode(message); return "Cannot decode"; } abstract protected bool MyAction( string message); abstract protected string DecodeString( string message); }
C#
270# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Code#Example#of#Chain#of#Responsibility#
class Decoder1 : Decoder { protected override bool MyAction( string message) { // see if I can do this. // if I can: // return true // if I can’t // return false } protected override string DecodeString( string message) {
String decodedMessage; //Decode the message
return decodedmessage; } } // other decoders follow this format as well.
C#
Page 138
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
271# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Code#Example#of#Chain#of#Responsibility#
class Client { public String decode( String message, Decoder aDecoder) { return aDecoder.decode( message); } } abstract class Decoder { private Decoder trailer; public Decoder ( Decoder nextDecoder) { trailer = nextDecoder; } public String decode ( String message) { if (myAction(message))
return decodeString( message); if (trailer!= null) return trailer.decode( message); return "Cannot decode"; } abstract protected boolean myAction( String message); abstract protected String decodeString( String message); }
Java
272# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Code#Example#of#Chain#of#Responsibility#
class Decoder1 extends Decoder { protected override boolean myAction( String message) { // see if I can do this. // if I can: // return true // if I can’t // return false } protected String decodeString( String message) {
String decodedMessage; //Decode the message
return decodedmessage; } } // other decoders follow this format as well.
Java
Page 139
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
273# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Code#Example#of#Chain#of#Responsibility#
bool Client::decode ( SubString message, Decoder aDecoder) { return aDecoder.decode( message); } class Decoder { public: Decoder(Decoder*); ~Decoder(); bool decode(string); protected: virtual bool myAction( string)= 0; private: Decoder *trailer; } Decoder::Decoder (Decoder* aDecoder) { trailer= aDecoder; } bool Decoder::decode ( string message) { if (myAction(message)) return(true); if (trailer!= null) return trailer->decode(message); else return false; } }
C++
274# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Code#Example#of#Chain#of#Responsibility#
class Decoder1 : public Decoder { public: protected: bool myAction( string message); } bool Decoder1::myAction( string message) { // see if can do this. // if can: // do it here // // return true // if can’t // return false } } // other decoders follow this format as well.
C++
Page 140
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
275# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
A#Focused#Example:#Poker#
Hand HandEvaluator
+eval(card[]):int
RoyalFlush
+eval(card[]):int
StraightFlush
+eval(card[]):int
4ofaKind
+eval(card[]):int
Flush
+eval(card[]):int
FullHouse
+eval(card[]):int
Straight
+eval(card[]):int
3ofaKind
+eval(card[]):int
Pair
+eval(card[]):int
HiCard
+eval(card[]):int
Encapsulated#Rules#
276# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
At#Run8me#
Hand RF
SF
4K
FH
FL
ST
3K
PR
HC
Page 141
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
277# ### #16#October#2013#
Vector'Forces'Discussion'
278# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Design##
! We#need#to#store#some#related#numbers.#! Let’s#store#them#in#consecu8ve#memory#loca8ons#
– What#do#we#call#it?###A#vector#
! Alternate#way#of#storing##– Store#a#number#along#with#a#reference#to#the#next#number.#
– What#do#we#call#it?##A#linked#list##
#
Page 142
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
279# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Forces#
Array Vector Linked List
Random Access Quick Quick Slow
Insert Client needs to make copy
Need to copy memory
Quick
Size per element Size of data Size of data
Size of data plus the reference
Cost of insert Allocate and copy Allocate and copy
Same every time
280# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Design#
! Vector##– Consecu8ve#memory#addresses#
– Use#index#to#select#element##
! Linked#list##– NonDconsecu8ve#memory#addresses##– Reference#to#next#element#in#list##
Page 143
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
281# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Implementa8on##
! Vector##– Allocate#memory#big#enough#to#hold#ini8al#elements#
– Ini8alize#each#element#to#null#or#0##
! Linked#List#– Set#ini8al#reference#to#null#– As#add#element,#update#the#reference##
– Make#sure#don’t#go#off#end#when#traversing##– Maybe#allocate#from#block#of#storage#to#avoid#severe#memory#block#use##
282# ### #16#October#2013#
Architectural'Pa*erns'
Page 144
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
283# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Architectural#PaWerns#
! Model#View#Controller#– Model#–#handles#data#and#rela8onships#
– View#–#displays#the#model#– Controller#–#interface#to#changing#the#model#
Controller#
Model#
View#
284# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Architectural#PaWerns#
! Pipes#and#Filters#(Unix)#– Document#to#spell#check##– Input#"#WordBreaker#"#Sorter#"#Unique#"#Dic8onaryCompare##
– Note:##Can#be#Decorator#paWern#on#lower#level#
! Cat#filename#|#sort#|#uniq#! Filter#/#pipe#/#filter#/#pipe###
A#B#C#A#A##
Becomes##A#
A#A#
B#
C##Becomes##
A#B#
C##
Page 145
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
285# ### #16#October#2013#
Inheritance'Versus'Interface'
286# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Inheritance#Issues##
! Inheritance#combines#two#perspec8ves#– Common#interface#(specifica8on)#
! Derived#classes#play#same#role#as#base#class##
– Common#implementa8on##! Inherited#methods,#aWributes#
! O_en#mix#up#these#perspec8ves###
Page 146
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
287# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Changing#Base#versus#Changing#Interface#
Base#Class#
MethodOne()#
AddedMethod()#//New#
Interface#
MethodOne()#
AddedMethod()#//#New#
Derived#Class#
Does#AddedMethod()#need#overriding#?##
Implemen8ng#Class#
AddedMethod()#needs#implementa8on#
288# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Inheritance#Versus#Interface#
BaseClass#Method();#
DerivedClass# AnotherDerivedClass#Method()#{#anotherWay;}##
How#to#avoid#redundancy?#
OneMore##DerivedClass#
Fourth#DerivedClass#Method()####{#anotherWay;}##
Page 147
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
289# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Inheritance#
BaseClass#Method();#
DerivedClass#
AnotherDerivedClass#
Create#hierarchy##
OneMore##DerivedClass#
Fourth#DerivedClass##
AnotherDerivedClass#Method()#{#anotherWay;}##
290# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Inheritance#
BaseClass#Method();#NewMethod();#
DerivedClass#NewMethod()#{someWay;}##
AnotherDerivedClass#
NewMethod()##Two#classes#need#same#override#
OneMore##DerivedClass#
Fourth#DerivedClass#NewMethod()#{someWay;}##
AnotherDerivedClass#Method()#{#anotherWay;}##
Page 148
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
291# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Interface#
Interface#Method();#
Implemen8ngClass#
AnotherImplemen8ngClass#InterfaceHelper#Method();#AnotherWay();##
OneMoreImplemen8ngClass#
FourthImplemen8ngClass#
292# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Inheritance#Versus#Interface#
Interface#Method();#NewMethod():#
Implemen8ngClass#
AnotherImplemen8ngClass#InterfaceHelper#Method();#AnotherWay();##NewMethod();#SomeWay();#
OneMoreImplemen8ngClass#
FourthImplemen8ngClass#
Page 149
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
293# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Prefactoring#Guideline#
! Avoid#premature#hierarchaliza8on##– Don’t#create#hierarchies#un8l#you#really#need#them##
! Easier#to#create#right#hierarchy#than#to#deDhierarchalize#the#wrong#one#
294# ### #16#October#2013#
Code'Notes'
Page 150
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
295# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Interfaces#and#Abstract#Classes#
! An#interface#– Defines#methods#and#their#signatures#
! An#abstract#class#– Defines#methods#and#their#signatures#– Can#include##
! Data#members#(aWributes)#! Method#implementa8ons#
! Class#can:#– Derive#from#abstract#class##
! O_en#only#from#one#class#(Java,#C#)#
– Implement#interface##! Can#implement#numerous#interfaces#
296# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Interface#and#Abstract#Classes#(2)#
! Interface#cannot#contain#sta8c#method#– So#some#examples#use#abstract#class##
– If#sta8c#method#is#in#another#class#(for#example#a#factory#class),#then#could#use#interface##
interface#MyInterface#####void#method();#
class#MyInterfaceHelper#####sta8c#MyInterface#getInstance();##
abstract#class#MyInterface#####void#method();#####sta8c#MyInterface#getInstance();###
class#MyClass####
class#MyClass####
Page 151
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
297# ### #16#October#2013#
Naming'
298# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Naming(1)#
! Six#character#names#(FORTRAN)###– CMPORB#,#ORBCMP##
– STRCMP##– Needs#comments##
! But#now?##– What’s#the#limit?### ##
Page 152
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
299# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Naming#(2)#
Class BfsSwsTpidConfigTable { BfsSwsTpidConfig TrySEHPBfsSwsTpidConfig() { try { int iRec = 0; int dwRecs = CountRecs(sizeof(BfsSwsTpidConfig)); while(iRec < dwRecs) { BfsSwsTpidConfig pbstc = (BfsSwsTpidConfig ) Pv() + iRec; if(pbstc.m_dwTPID == _dwTPID) { return pbstc; } ++iRec; } } }
300# ### #16#October#2013#
Commonality5Variability'Analysis'
Page 153
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
301# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
CommonalityDVariability#Analysis#
! Abstrac8on##focuses#on#commonality#(general)#! DeDemphasize#variable#details##(specifics)#.#! Acknowledgement:##
– Commonality#–#Variability#Analysis#in#James#Coplien’s#Mul8Dparadigm#Design#for#C++#
His#thesis#is#on#line#at#hWp://www.netobjec8ves.com/download/CoplienThesis.pdf#
c#
Paradigm00PaKerns0
Wisdom0Principles0 Prac+ces0
Quali+es##
His#thesis#is#on#line#at:#hWp://www.netobjec8ves.com/files/CoplienThesis.pdf#(link#is#caseDsensi8ve)#
302# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Commonali8es#and#Variability#
! Commonali8es#can#define#basic#domain#concepts#– Recognized#from#experience#
– Learned#through#analysis#(abstracted)#! Variability#is#varia8on#of#commonality##
! From#an#architectural#perspec8ve:#– Commonality#analysis#gives#architecture#its#longevity;##– Variability#analysis#drives#its#fitness#for#use”*#
*'MulB<Paradigm%Design%in%C++,#Jim#Coplien#
Page 154
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
303# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Abstrac8on#Longevity##
Longevity###Interface#Car#####turn()####speedUp()####slowDown()#
Implementa8on#VW#####turn()####speedUp()####slowDown()#
Implementa8on#BMW####turn()####speedUp()####slowDown()#
Implementa8on#Yugo####turn()####speedUp()####slowDown()#
304# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Steps##
! Steps#to#follow:#– Pick#something#in#problem#domain#– Ask#is#it?#
! A#par8cular#way#of#doing#something#(a#varia8on)?#– If#so,##what#concept#is#it#a#varia8on#of?# # ##
! Or#! A#way#of#conceptually#thinking#about#different#ways#to#do#things?#
– If#so,#iden8fy#as#a#concept#! If#neither##
– (just#a#standalone#func8on)#,#iden8fy#it#as#an#en8ty#
not in sem
Page 155
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
305# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Commonality–Variability#Analysis#Exercise#
! Have#to#handle#European#date#formats#as#well#as#US#date#format#
! US#Tax#! Canadian#PST,#GST#! European#VAT#! German#Shipping#Rates#! French#Freight#Rules#! Verifica8on#of#valid#addresses#
in#different#countries#
! Max#Weight#in#US#is#70#lbs#! Canadian#Freight#Rules#! US#Freight#Rules#! US#Phone##s#! European#Phone##s#! Max#Weight#in#Germany#is#40#
kg#! Euros#in#Europe,#Dollars#in#
US,#etc…#
Say#we’re#given#the#following#requirements#for#an#eDcommerce#system:#
#
306# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
CVA#and#OO#Rela8onships#
! CVA#does#not#deal#with#rela8ng#concepts#– E.G.#US$#in#US,#Euro#in#Germany.###
! Money#and#country0are#“related”#
– US$##and#Euro#varia8on#of#money##! Not#of#country##
! CVA#says:#– First#find#Commonali8es#and#Variability's#
! Limit#to#isDa#rela8onship#
– Then#iden8fy#interDrela8onships#later#! Will#use#paWerns#to#implement#rela8onships##
Page 156
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
307# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Discussion#Exercise#
! For#the#eDcommerce#system##– Iden8fy#commonali8es#and#variability's#present#in#the#problem#domain#
– First#iden8fy#commonali8es#! Then#iden8fy#varia8ons#within#these#commonali8es#
not in sem 308# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Work#Space#
Page 157
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
309# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Work#Space#
310# #Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Work#Space#
Page 158
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
311# #Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Work#Space#
312# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Some#Commonali8es#and#Variabili8es#
! Con8nents#– European#– North#American#
! Countries#– France#– Germany#– Canada#– US#
! Taxes#– European#– Canadian#– US#
! Money#– US#$#– Canadian#$#– Euro#
! Phone###Formats#– European#– US/Canadian#
! Shipping#Rules#– French#– German#– Canadian#
! Date#Formats##– yyyy/mm/dd#– dd/mm/yyyy#– mm/dd/yyyy#
! Freight#Rates#– German#Rates#– French#Rates#– Canadian#Rates#
! Shipping#– Truck#– Plane#– Rail#– Ship#
! Max#Weights#– German##D#40#kg#– French#–#none#– Canada#–#none#– US#D#70#lbs#
! Address#Verifica8on#– French#– German#– Canadian#– US# Note:#If#Units#are#abstracted,#
perhaps#Max0Weights0can#simply#be#an#aWribute/value#
Page 159
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
313# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Notes#about#Commonali8es#and#Their#Varia8ons#
! CVA#is#just#a#star8ng#point.##Suggests:##– Concepts#D>#abstract#interfaces#– Varia8on#D>#concrete#types#
! Not#all#commonali8es#and#varia8ons#are#useful#– Some#describe#varia8ons#implementable#by#changing#an#aWribute#value#(e.g.,#finance#charge#rate)#
314# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Ways#To#Handle#Varia8on#
! PaWerns#–#Strategy,#others#! Tables#–#Lookup#value##! Pass#in#values#
Concept / Variation US Canada Germany
Max weight 70 lbs none 40 kg
Page 160
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
315# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Exercise#D#Which#Way?#
Varia8ons#(e.g.#Countries)#
Concepts#(e.g.)#Address#Verifica8on##
316# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Handling#Varia8ons##D#(1)##
int getMaximumWeight(Locale locale) { switch(locale)
{ case US:
return 70; case Canada
return UNLIMITED; //…
// Or a table lookup }
String getDateAsString(Locale locale, Date date)
{ switch(locale)
{ case US:
return date.FormattedAs(locale); //…..
Page 161
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
317# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Handling#Varia8ons#(2)##
interface Details { int getMaximumWeight(); getDateAsString(Date date); }; class US implements Details { int getMaximumWeight() { return 70; } String getDateAsString) Date date){ return date.FormattedAs(US);} } class Canada implements Details { int getMaximumWeight() { return UNLIMITED; } String getDateAsString) Date date){ return date.FormattedAs(CANADA);} }
318# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
Using#CommonalityDVariability##Analysis#to#Design#Class#Structures#
Commonalityanalysis
Variabilityanalysis
Conceptualperspective
Specificationperspective
Implementationperspective
Interface
Operations
Concreteclass
Operations
Concreteclass
Operations
Page 162
Design'Pa*erns'Explained'
16#October#2013#Copyright#©#2007#Net#Objec8ves.#All#Rights#Reserved.#
319# #Copyright#©#2013##Net#Objec8ves.#All#Rights#Reserved.## #16#October#2013#
How#Do#Abstrac8ons#/#CVA#Relate#to#PaWerns?#
! PaWerns#reflect#separa8on#that#good#abstrac8ons#create#in#design#
! PaWerns#proceed#from#CVA#! CVA#can#be#used#to#discover#paWerns#(to#be#shown#shortly)##