![Page 1: Použití návrhových vzorů v prostředí jazyka C# .NET](https://reader035.vdocuments.pub/reader035/viewer/2022062500/568151bb550346895dbfe9a5/html5/thumbnails/1.jpg)
Použití návrhových vzorů v prostředí jazyka C# .NET
Bc. Michal JakubecMCSE, MCSD, MCDBA, MCTS
http://www.jakubec.cz/
1
![Page 2: Použití návrhových vzorů v prostředí jazyka C# .NET](https://reader035.vdocuments.pub/reader035/viewer/2022062500/568151bb550346895dbfe9a5/html5/thumbnails/2.jpg)
Agenda
• 17:00 až 17:10 – Představení WUGu• 17:10 až 18:30 – Návrhové vzory GoF• 18:30 až 18:45 – Přestávka a občerstvení• 18:45 až 20:00 – Návrhové vzory v praxi• 20:00 – Diskuse: postřehy z praxe
2
![Page 3: Použití návrhových vzorů v prostředí jazyka C# .NET](https://reader035.vdocuments.pub/reader035/viewer/2022062500/568151bb550346895dbfe9a5/html5/thumbnails/3.jpg)
Návrhové vzory GoF1. část
3
![Page 4: Použití návrhových vzorů v prostředí jazyka C# .NET](https://reader035.vdocuments.pub/reader035/viewer/2022062500/568151bb550346895dbfe9a5/html5/thumbnails/4.jpg)
Co je návrhový vzor?
• Definice„Obecně použitelné řešení
určitého problému v určitém kontextu“• Specifikace
– Název vzoru– Popis problému– Popis řešení– Důsledky použití vzoru, příp. alternativy
4
![Page 5: Použití návrhových vzorů v prostředí jazyka C# .NET](https://reader035.vdocuments.pub/reader035/viewer/2022062500/568151bb550346895dbfe9a5/html5/thumbnails/5.jpg)
K čemu je to dobré?
• Společný slovník vývojářů a architektů• Nemusíte "objevovat kolo"• Velice inspirativní pro další profesní rozvoj• Rozvíjí návrhové schopnosti• Usnadňují řešení návrhových a vývojových
problémů (většinou)• Vedou k získání tvárnější implementace
funkčnosti (většinou)
5
![Page 6: Použití návrhových vzorů v prostředí jazyka C# .NET](https://reader035.vdocuments.pub/reader035/viewer/2022062500/568151bb550346895dbfe9a5/html5/thumbnails/6.jpg)
Jak začít s návrhovými vzory?
• Pořiďte si knihu GoF a mějte ji po ruce• Seznamte se s UML• Připravte si tužku a papír
– později postačí propiska• Diskutujte o vzorech a svých návrzích s kolegy• Mějte odhodlání a pevnou vůli
– abstrakci se člověk učí celý život
6
![Page 7: Použití návrhových vzorů v prostředí jazyka C# .NET](https://reader035.vdocuments.pub/reader035/viewer/2022062500/568151bb550346895dbfe9a5/html5/thumbnails/7.jpg)
Klasifikace vzorů GoF
7
Účel Přístup
Tvorba instancí(Creational)
Struktura(Structural)
Chování(Behavioral)
Třída Factory Method Adapter (C) InterpreterTemplate Method
Instance Abstract Factory BuilderPrototypeSingleton
Adapter (I)BridgeCompositeDecoratorFaçadeFlyweightProxy
Chain of ResponsibilityCommandIteratorMediatorMementoObserverStateStrategyVisitor
![Page 8: Použití návrhových vzorů v prostředí jazyka C# .NET](https://reader035.vdocuments.pub/reader035/viewer/2022062500/568151bb550346895dbfe9a5/html5/thumbnails/8.jpg)
Vzájemné vztahy vzorů GoF
8
![Page 9: Použití návrhových vzorů v prostředí jazyka C# .NET](https://reader035.vdocuments.pub/reader035/viewer/2022062500/568151bb550346895dbfe9a5/html5/thumbnails/9.jpg)
Zadání ukázkové aplikace
• Vytvořte aplikaci, která umožní– zadání jednoduchého algebraického výrazu s
konstantami a proměnnými v textové formě– zadání hodnot jednotlivých proměnných ve výrazu– vyhodnocení výrazu a zobrazení výsledku
9
![Page 10: Použití návrhových vzorů v prostředí jazyka C# .NET](https://reader035.vdocuments.pub/reader035/viewer/2022062500/568151bb550346895dbfe9a5/html5/thumbnails/10.jpg)
Vzory GoF v praktické ukázce
• Composite (Skladba)• Builder (Stavitel)• Interpreter (Interpret)• Command (Příkaz)
…možná naleznete nějaké další
10
![Page 11: Použití návrhových vzorů v prostředí jazyka C# .NET](https://reader035.vdocuments.pub/reader035/viewer/2022062500/568151bb550346895dbfe9a5/html5/thumbnails/11.jpg)
Podoba uživatelského rozhraní
11
Kalkulátor algebraických výrazů
a - (b + c)
Výraz:
a = 12, b = 3, c = 5
Proměnné:
4
Výsledek:
ZavřítVypočítat
X
Smazat
http://www.infoq.com/presentations/Modeling-the-User-Interface
![Page 12: Použití návrhových vzorů v prostředí jazyka C# .NET](https://reader035.vdocuments.pub/reader035/viewer/2022062500/568151bb550346895dbfe9a5/html5/thumbnails/12.jpg)
Gramatika platných výrazů
Zápis v Backusově-Naurově formě (BNF):
<expr> ::= <number> | <var> | <expr> <oper> <expr> | "(" <expr> ")"<oper> ::= '+' | '-' | '*' | '/'<number> ::= <digit> | <digit> <number><digit> ::= "0" | "1" | "2" | … | "9"<var> ::= <letter> | <letter> <var><letter> ::= "a" | "b" | "c" | ... | "z"
Možný výskyt bílých znaků (mezery, tabulátory, apod.) v definici pro přehlednost neuvádím.
12
![Page 13: Použití návrhových vzorů v prostředí jazyka C# .NET](https://reader035.vdocuments.pub/reader035/viewer/2022062500/568151bb550346895dbfe9a5/html5/thumbnails/13.jpg)
Příklady vyhovující gramatice
• 36• a + b• 12 + c• 5 + a * 9 + b – c• 5 + (a * 9) + b – c• (abc + xyz) / opq• (24 + (b * 3)) / (a – 2)
13
![Page 14: Použití návrhových vzorů v prostředí jazyka C# .NET](https://reader035.vdocuments.pub/reader035/viewer/2022062500/568151bb550346895dbfe9a5/html5/thumbnails/14.jpg)
Zachycení hodnot proměnných
• Kolekce typu klíč-hodnota
14
Název proměnné (klíč kolekce) Hodnota proměnné
a 26
b 38
… …
![Page 15: Použití návrhových vzorů v prostředí jazyka C# .NET](https://reader035.vdocuments.pub/reader035/viewer/2022062500/568151bb550346895dbfe9a5/html5/thumbnails/15.jpg)
Zachycení výrazu v paměti
(24 + (b * 3)) / (a – 2)
15
/
+ -
24 *
b 3
2a
KořenBinární strom
Konstanta
Binární výraz
Proměnná
![Page 16: Použití návrhových vzorů v prostředí jazyka C# .NET](https://reader035.vdocuments.pub/reader035/viewer/2022062500/568151bb550346895dbfe9a5/html5/thumbnails/16.jpg)
Vzor Composite (Skladba)
• skládáním jednoduchých objektů získáme funkční celek
16
![Page 17: Použití návrhových vzorů v prostředí jazyka C# .NET](https://reader035.vdocuments.pub/reader035/viewer/2022062500/568151bb550346895dbfe9a5/html5/thumbnails/17.jpg)
Zachycení výrazu – Composite
17
«interface»IExpression
Symbol : string
BinaryExpression
Name : string
VariableExpression
Value : double
ConstantExpression
Left
Right
![Page 18: Použití návrhových vzorů v prostředí jazyka C# .NET](https://reader035.vdocuments.pub/reader035/viewer/2022062500/568151bb550346895dbfe9a5/html5/thumbnails/18.jpg)
Praktická ukázka (1/5)
• Implementace zachycení výrazu– rozhraní IExpression– třída ConstantExpression– třída VariableExpression– třída BinaryExpression
• Doplnění překrytí metody ToString()– umožní zobrazení textové podoby výrazu –
užitečné pro ladění
18
![Page 19: Použití návrhových vzorů v prostředí jazyka C# .NET](https://reader035.vdocuments.pub/reader035/viewer/2022062500/568151bb550346895dbfe9a5/html5/thumbnails/19.jpg)
Vzor Builder (Stavitel)
• Odděluje konstrukci složeného objektu od jeho reprezentace
19
![Page 20: Použití návrhových vzorů v prostředí jazyka C# .NET](https://reader035.vdocuments.pub/reader035/viewer/2022062500/568151bb550346895dbfe9a5/html5/thumbnails/20.jpg)
20
Tvorba stromu výrazu – Builder
+ 1 2 1 + 2 1 2 +
BuildConstant(value : double)BuildVariable(name : string)BuildOperation(symbol : string)BuildLeftBracket()BuildRightBracket()GetProduct() : IExpression
«interface»IExpressionBuilder
ExpressionParser(builder : IExpressionBuilder)Parse(text : string) : IExpression
ExpressionParserbuilder
InfixExpressionBuilder PostfixExpressionBuilderPrefixExpressionBuilder
![Page 21: Použití návrhových vzorů v prostředí jazyka C# .NET](https://reader035.vdocuments.pub/reader035/viewer/2022062500/568151bb550346895dbfe9a5/html5/thumbnails/21.jpg)
Praktická ukázka (2/5)
• Implementace tvorby stromu výrazu– rozhraní IExpressionBuilder– třída ExpressionParser– třída InfixExpressionBuilder
21
![Page 22: Použití návrhových vzorů v prostředí jazyka C# .NET](https://reader035.vdocuments.pub/reader035/viewer/2022062500/568151bb550346895dbfe9a5/html5/thumbnails/22.jpg)
Vzor Interpreter (Interpret)
• Definuje reprezentaci gramatiky a způsob jejího vyhodnocení (interpretace)
22
![Page 23: Použití návrhových vzorů v prostředí jazyka C# .NET](https://reader035.vdocuments.pub/reader035/viewer/2022062500/568151bb550346895dbfe9a5/html5/thumbnails/23.jpg)
23
Výpočet výrazu – Interpreter
GetValue(string name) : double
«interface»IContext
Evaluate(context : IContext) : double
«interface»IExpression
Context(items : Dictionary<string, double>)GetValue(name : string) : double
items : Dictionary<string, double>
DictionaryContext// pro ConstantExpression return value;
// pro VariableExpression return context.GetValue(name);
// pro BinaryExpression sčítání return left.Evaluate(context) + right.Evaluate(context);
![Page 24: Použití návrhových vzorů v prostředí jazyka C# .NET](https://reader035.vdocuments.pub/reader035/viewer/2022062500/568151bb550346895dbfe9a5/html5/thumbnails/24.jpg)
Praktická ukázka (3/5)
• Implementace výpočtu výrazu– rozhraní IContext– metoda IExpression.Evaluate(IContext)– třída DictionaryContext
24
![Page 25: Použití návrhových vzorů v prostředí jazyka C# .NET](https://reader035.vdocuments.pub/reader035/viewer/2022062500/568151bb550346895dbfe9a5/html5/thumbnails/25.jpg)
25
Tvorba kontextu – Builder
BuildName(name : string)BuildValue(value : double)BuildAssignment()BuildDelimiter()GetProduct() : IContext
«interface»IContextBuilder
ContextParser(builder : IContextBuilder)Parse(text : string) : IContext
ContextParserbuilder
DictionaryContextBuilder LinkedListContextBuilderArrayContextBuilder
![Page 26: Použití návrhových vzorů v prostředí jazyka C# .NET](https://reader035.vdocuments.pub/reader035/viewer/2022062500/568151bb550346895dbfe9a5/html5/thumbnails/26.jpg)
Praktická ukázka (4/5)
• Implementace tvorby kontextu– rozhraní IContextBuilder– třída ContextParser– třída DictionaryContextBuilder
26
![Page 27: Použití návrhových vzorů v prostředí jazyka C# .NET](https://reader035.vdocuments.pub/reader035/viewer/2022062500/568151bb550346895dbfe9a5/html5/thumbnails/27.jpg)
Vzor Command (Příkaz)
• Zapouzdří operaci tak, aby bylo možné ji předávat a užívat různými subjekty
27
![Page 28: Použití návrhových vzorů v prostředí jazyka C# .NET](https://reader035.vdocuments.pub/reader035/viewer/2022062500/568151bb550346895dbfe9a5/html5/thumbnails/28.jpg)
Napojení na UI - Command
28
Execute()
«interface»ICommand
ButtonCalculate_Click()ToolbarCalculate_Click()
MainFormcommand
command.Execute();
CalculationCommand( entryExpression : Control, entryVariables : Control, entryResult : Control)Execute()
CalculationCommand
![Page 29: Použití návrhových vzorů v prostředí jazyka C# .NET](https://reader035.vdocuments.pub/reader035/viewer/2022062500/568151bb550346895dbfe9a5/html5/thumbnails/29.jpg)
Praktická ukázka (5/5)
• Implementace napojení na UI– rozhraní ICommand– třída CalculationCommand– deklarace atributu typu ICommand– vytvoření instance CalculationCommand
29
![Page 30: Použití návrhových vzorů v prostředí jazyka C# .NET](https://reader035.vdocuments.pub/reader035/viewer/2022062500/568151bb550346895dbfe9a5/html5/thumbnails/30.jpg)
Shrnutí
• Vzor Composite (Skladba)– zachycení struktury algebraického výrazu
• Vzor Builder (Stavitel)– tvorba stromu výrazu z jeho textové podoby– tvorba kontextu z jeho textové podoby
• Vzor Interpreter (Interpret)– výpočet hodnoty výrazu dle kontextu
• Vzor Command (Příkaz)– napojení na UI
• … nějaké další vzory?30
![Page 31: Použití návrhových vzorů v prostředí jazyka C# .NET](https://reader035.vdocuments.pub/reader035/viewer/2022062500/568151bb550346895dbfe9a5/html5/thumbnails/31.jpg)
Trochu historie…• Christopher Alexander:
A Pattern Language, 1977• Kent Beck, Ward Cunningham: Using Pattern Languages
for Object-Oriented Programs, OOPSLA, 1987• GoF: Design Patterns, OOPSLA, 1994
31
![Page 32: Použití návrhových vzorů v prostředí jazyka C# .NET](https://reader035.vdocuments.pub/reader035/viewer/2022062500/568151bb550346895dbfe9a5/html5/thumbnails/32.jpg)
GoF: Gang of FourRalph Johnson, Erich Gamma,Richard Helm, John Vlissides
32
![Page 33: Použití návrhových vzorů v prostředí jazyka C# .NET](https://reader035.vdocuments.pub/reader035/viewer/2022062500/568151bb550346895dbfe9a5/html5/thumbnails/33.jpg)
Rok 2005: 10. výročí vzorů GoF
33
Zdroj: http://laputan.org/
![Page 34: Použití návrhových vzorů v prostředí jazyka C# .NET](https://reader035.vdocuments.pub/reader035/viewer/2022062500/568151bb550346895dbfe9a5/html5/thumbnails/34.jpg)
PřestávkaObčerstvení, názory, připomínky, otázky, odpovědi…
34
![Page 35: Použití návrhových vzorů v prostředí jazyka C# .NET](https://reader035.vdocuments.pub/reader035/viewer/2022062500/568151bb550346895dbfe9a5/html5/thumbnails/35.jpg)
Návrhové vzory v praxi3. část
35
![Page 36: Použití návrhových vzorů v prostředí jazyka C# .NET](https://reader035.vdocuments.pub/reader035/viewer/2022062500/568151bb550346895dbfe9a5/html5/thumbnails/36.jpg)
Typické problémy ze života
• Decorator vs. Proxy• Mediator vs. Observer• Visitor vs. Interpreter• Singleton v různých podobách
36
![Page 37: Použití návrhových vzorů v prostředí jazyka C# .NET](https://reader035.vdocuments.pub/reader035/viewer/2022062500/568151bb550346895dbfe9a5/html5/thumbnails/37.jpg)
Decorator vs. Proxy
• Decorator– skládá funkčnost
objektů– zachovává rozhraní
• Proxy– upravuje
funkčnostobjektu
– zachovávározhraní
37
![Page 38: Použití návrhových vzorů v prostředí jazyka C# .NET](https://reader035.vdocuments.pub/reader035/viewer/2022062500/568151bb550346895dbfe9a5/html5/thumbnails/38.jpg)
Mediator vs. Observer
• Mediator– fixní vztahy
(většinou)
• Observer– variabilní
vztahy(většinou)
38
Otázka: Najdete v těchto diagramech syntaktickou chybu?
![Page 39: Použití návrhových vzorů v prostředí jazyka C# .NET](https://reader035.vdocuments.pub/reader035/viewer/2022062500/568151bb550346895dbfe9a5/html5/thumbnails/39.jpg)
Visitor vs. Interpreter
• Visitor– visitor se při
průchodu mění
• Interpreter– kontext se při
průchodu nemění
39
![Page 40: Použití návrhových vzorů v prostředí jazyka C# .NET](https://reader035.vdocuments.pub/reader035/viewer/2022062500/568151bb550346895dbfe9a5/html5/thumbnails/40.jpg)
Singleton v různých podobách
• veřejný statický atributinternal sealed class Singleton{ public static readonly Singleton Instance = new Singleton();
private Singleton() { ... }}
40
![Page 41: Použití návrhových vzorů v prostředí jazyka C# .NET](https://reader035.vdocuments.pub/reader035/viewer/2022062500/568151bb550346895dbfe9a5/html5/thumbnails/41.jpg)
Singleton v různých podobách
• veřejná statická vlastnostinternal sealed class Singleton{ private static readonly Singleton instance = new Singleton();
public static Singleton Instance { get { return instance; } }
private Singleton() { ... }}
41
![Page 42: Použití návrhových vzorů v prostředí jazyka C# .NET](https://reader035.vdocuments.pub/reader035/viewer/2022062500/568151bb550346895dbfe9a5/html5/thumbnails/42.jpg)
Singleton v různých podobách
• veřejná statická vlastnost jako proxyinternal sealed class Singleton{ private static Singleton instance;
public static Singleton Instance { get { if (instance == null) instance = new Singleton(); return instance; } }
private Singleton() { ... }}
42
![Page 43: Použití návrhových vzorů v prostředí jazyka C# .NET](https://reader035.vdocuments.pub/reader035/viewer/2022062500/568151bb550346895dbfe9a5/html5/thumbnails/43.jpg)
Singleton v různých podobách
• synchronizace vícevláknového přístupu (jde to lépe?)internal sealed class Singleton{ private static volatile Singleton instance;
public static Singleton Instance { get { lock(typeof(Singleton)) { if (instance == null) instance = new Singleton(); return instance; } } }
private Singleton() { ... }}
43
![Page 44: Použití návrhových vzorů v prostředí jazyka C# .NET](https://reader035.vdocuments.pub/reader035/viewer/2022062500/568151bb550346895dbfe9a5/html5/thumbnails/44.jpg)
Singleton v různých podobách
• synchronizace vícevláknového přístupu (lepší varianta)internal sealed class Singleton{ private static object syncRoot = new object(); private static volatile Singleton instance;
public static Singleton Instance { get { lock(syncRoot) { if (instance == null) instance = new Singleton(); return instance; } } }
private Singleton() { ... }} 44
![Page 45: Použití návrhových vzorů v prostředí jazyka C# .NET](https://reader035.vdocuments.pub/reader035/viewer/2022062500/568151bb550346895dbfe9a5/html5/thumbnails/45.jpg)
Singleton v různých podobách
• double-checked locking optimizationinternal sealed class Singleton{ private static object syncRoot = new object(); private static volatile Singleton instance; public static Singleton Instance { get { if (instance == null) { lock(syncRoot) { if (instance == null) instance = new Singleton(); } } return instance; } } private Singleton() { ... }}
45
![Page 46: Použití návrhových vzorů v prostředí jazyka C# .NET](https://reader035.vdocuments.pub/reader035/viewer/2022062500/568151bb550346895dbfe9a5/html5/thumbnails/46.jpg)
O vzorech EAA
• hlavním autorem Martin Fowler– http://www.martinfowler.com
• zejména architektonické a návrhové vzory• vzory připraveny na základě bohatých
zkušeností autora z tvorby business aplikací
46
![Page 47: Použití návrhových vzorů v prostředí jazyka C# .NET](https://reader035.vdocuments.pub/reader035/viewer/2022062500/568151bb550346895dbfe9a5/html5/thumbnails/47.jpg)
Přehled vzorů EAA• Domain Logic Patterns
– Transaction Script (110), Domain Model (116), Table Module (125), Service Layer (133).
• Data Source Architectural Patterns– Table Data Gateway (144), Row Data Gateway
(152), Active Record (160), Data Mapper (165).
• Object-Relational Behavioral Patterns:– Unit of Work (184), Identity Map (195), Lazy Load
(200)
• Object-Relational Structural Patterns:– Identity Field (216), Foreign Key Mapping (236),
Association Table Mapping (248), Dependent Mapping (262), Embedded Value (268), Serialized LOB (272), Single Table Inheritance (278), Class Table Inheritance (285), Concrete Table Inheritance (293), Inheritance Mappers (302).
• Object-Relational Metadata Mapping Patterns:– Metadata Mapping (306), Query Object (316),
Repository (322).
• Web Presentation Patterns:– Model View Controller (330), Page Controller
(333), Front Controller (344), Template View (350), Transform View (361), Two-Step View (365), Application Controller (379).
• Distribution Patterns:– Remote Facade (388), Data Transfer Object
(401)
• Offline Concurrency Patterns:– Optimistic Offline Lock (416),
Pessimistic Offline Lock (426), Coarse Grained Lock (438), Implicit Lock (449).
• Session State Patterns:– Client Session State (456), Server Session State
(458), Database Session State (462).
• Base Patterns:– Gateway (466), Mapper (473), Layer Supertype
(475), Separated Interface (476), Registry (480), Value Object (486), Money (488), Special Case (496), Plugin (499), Service Stub (504), Record Set (508)
47
Zdroj: http://martinfowler.com/eaaCatalog/
![Page 48: Použití návrhových vzorů v prostředí jazyka C# .NET](https://reader035.vdocuments.pub/reader035/viewer/2022062500/568151bb550346895dbfe9a5/html5/thumbnails/48.jpg)
Praktická ukázka (1/2)
• Domain Model – třídy reprezentující prvky výrazu a hodnoty proměnných
• Repository – hlavní přístupový bod k mechanismu persistence výrazů a hodnot proměnných
48
![Page 49: Použití návrhových vzorů v prostředí jazyka C# .NET](https://reader035.vdocuments.pub/reader035/viewer/2022062500/568151bb550346895dbfe9a5/html5/thumbnails/49.jpg)
Princip Inversion of Control (IoC)
49
![Page 50: Použití návrhových vzorů v prostředí jazyka C# .NET](https://reader035.vdocuments.pub/reader035/viewer/2022062500/568151bb550346895dbfe9a5/html5/thumbnails/50.jpg)
Dependency Injection
• Tři základní metody „kontejnerové“ injekce– pomocí konstruktorů– pomocí setterů– pomocí „injekčních“ rozhraní
• Alternativa pomocí EAA vzoru Registry– statické rozhraní – „pevné“ metody vrací produkt– dynamické rozhraní – produkt získáván z kolekce
či pomocí reflexe
50
![Page 51: Použití návrhových vzorů v prostředí jazyka C# .NET](https://reader035.vdocuments.pub/reader035/viewer/2022062500/568151bb550346895dbfe9a5/html5/thumbnails/51.jpg)
Praktická ukázka (2/2)
• Dependency Injection – výměna implementace mechanismu persistence
• Adapter (GoF) – doplňková funkčnost k mechanismu persistence výrazů
51
![Page 52: Použití návrhových vzorů v prostředí jazyka C# .NET](https://reader035.vdocuments.pub/reader035/viewer/2022062500/568151bb550346895dbfe9a5/html5/thumbnails/52.jpg)
Zdroje
• http://sourcemaking.com/• http://martinfowler.com/eaaCatalog/index.html• http://martinfowler.com/articles/injection.html
52
![Page 53: Použití návrhových vzorů v prostředí jazyka C# .NET](https://reader035.vdocuments.pub/reader035/viewer/2022062500/568151bb550346895dbfe9a5/html5/thumbnails/53.jpg)
Závěr: Diskuse: názory, připomínky, otázky, odpovědi
53