curs 7 - alexandru ioan cuza universityogh/files/ip/curs-07.pdf · deveni familiar şi îl vor...
TRANSCRIPT
Ingineria Program ării
Curs 7Curs 7
Ovidiu Gheorghieş, [email protected]
Adriana Gheorghieş, [email protected]
Design Patterns, I
Modele de proiectare, I
IP7
Design Patterns(Modele de proiectare)
• de·sign n.– 1.a. A drawing or sketch. – b. A graphic representation, especially a detailed plan for
construction or manufacture.– 2. The purposeful or inventive arrangement of parts or
details.– 3. The art or practice of designing or making designs.
• pat·tern n.– 1.a. A model or an original used as an archetype.– b. A person or thing considered worthy of imitation.– 2. A plan, diagram, or model to be followed in making things
IP7 MotivaŃii
• Proiectarea sistemelor (orientate-obiect) este dificilă
• Proiectarea sistemelor (orientate-obiect) extensibile este foarte dificilă
• Proiectarea sistemelor (orientate-obiect) refolosibile este şi mai dificilă
• Scopuri în proiectare– Rezolvarea problemei concrete– Crearea unei structuri flexibile, ce poate evolua– Evitarea re-proiectării
IP7 Proiectare bună
• Este greu (pentru începători) să creeze un proiect bun de prima dată
• ProiectanŃii experŃi reuşesc repede deoarece:– Refolosesc soluŃii folosite în proiecte anterioare– [ ExperienŃa crează experŃii ]
• Apar modalităŃi standard de a rezolva probleme concrete. Familiaritatea cu acestea poate duce la crearea unui proiect flexibil, elegant şi reutilizabil într-un timp scurt.
IP7 Surse de inspiraŃie
•Antropologie culturală“antropologie = ştiinŃă care se ocupă cu studiul originii, evoluŃiei şi variabilităŃii biologice a omului, în corelaŃie cu condiŃiile naturale şi socio-culturale.” (DEX)
•Arhitectură“ştiinŃa şi arta de a proiecta şi construi clădiri” (DEX)
IP7 Antropologia culturală
• FrumuseŃea stă în ochii celui care priveşte sau oamenii admit (acceptă) faptul că anumite lucruri sunt frumoase iar altele nu?
• Într-o cultură indivizii cad de acord, în mare parte, asupra a ceea ce este considerat frumos.
• Cultura transcende credinŃele individuale.
IP7 Arhitectură
Cristopher Alexander (arhitect american):• “Este calitatea obiectivă?”
• Calitatea unei construcŃii poate fi măsurată în mod obiectiv, ea nu este numai o chestiune de gust.
• Pattern = soluŃie la o problemă într-un anumit context.
IP7 Design bun, design prost…
• Cum ne dăm seama că un anumit design este bun?
– Ce este prezent într-un design bun şi nu se regăseşte într-un design prost?
– Ce este prezent intr-un design prost şi nu se regaseşte într-un design bun?
IP7 Exemplu: curtea unei case
• Curtea unei case ajută oamenii să trăiască în ea.• Oamenii doresc să aibă un spaŃiu propriu în aer liber
în care să poată admira cerul şi stelele, să se bucure de soare şi, poate, să planteze flori.
• Dar mai sunt şi alte lucruri de luat în considerare. De exemplu, atunci când o curte are ziduri care nu permit vederea în exterior oamenii nu se simt bine şi tind să stea deoparte... ei au nevoie să vadă în exterior, ei au nevoie de spaŃii largi.
• Pe de altă parte oamenii îşi creează obişnuinŃe. Dacă ei trec zilnic încoace şi încolo prin curte locul le va deveni familiar şi îl vor folosi.
nume scop
desc
riere
a pr
oble
mei
IP7 Bibliografie
Erich Gamma, Richard Helm, Ralph Johnson, John Vlissides.Design Patterns. Elements of Reusable Object-Oriented Software.Addison-Wesley, 1995
Pe scurt GOF = Gang of Four
În română:
Şabloane de proiectare. Elemente de software reutilizabil orientat pe obiect
Editura Teora, 2002
IP7
“Design patterns capture solutions that have developed and evolved over time”
GOF
IP7
Elementele unui model de proiectare
• Numele– Mod de a referi o problemă de proiectare, soluŃiile ei şi
consecinŃele acestora.– ÎmbogăŃeşte limbajul proiectantului– Găsirea numelui: cea mai dificilă problemă
• Problema– Descrie problema şi contextul în care apare
• SoluŃia– Descrie elementele modelului, relaŃiile, resposabilităŃile şi modul de colaborare.
– Nu este o soluŃie concretă, ci una abstractă
• ConsecinŃele
IP7 Modele de proiectare - clasificare
• modele structurale: se preocupă de modul în care clasele şi obiectele sunt compuse pentru a forma structuri mai mari
(adapter, bridge, composite, decorator, façade, flyweight, proxy)
• modele comportamentale: se preocupă de algoritmi şi de asignarea responsabilităŃilor între obiecte
(chain of responsibility, command, interpreter, iterator, mediator, memento, observer, state, strategy, template method, visitor)
• modele creaŃionale: abstractizează procesul de instanŃiere
(abstract factory, builder, factory method, prototype, singleton)
IP7 În acest curs
• Singleton: garantează existenŃa unei singure instanŃe a unei clase. Se asigură o modalitate de a accesa instanŃa respectivă.
• Factory Method: defineşte o interfaŃă pentru crearea unui obiect, dar lasă în sarcina subclaselor alegerea tipului acestuia.
• Strategy: defineşte o familie de algoritmi
• Decorator: asignare de responsabilităŃi în mod dinamic
• Composite: obiecte şi grupuri tratate uniform
• Iterator: oferă o modalitate de a accesa obiecte agregate în mod secvenŃial fără a cunoaşte modul de agregare
• Template Method: se defineşte scheletul unui algoritm într-o metodă, lăsând implementarea paşilor algoritmului în seama subclaselor
IP7 Singleton / Unicat
• Scop: Garantarea existenŃei unei singure instanŃe a unei clase. Se asigură o modalitate de a accesa instanŃa respectivă.
• MotivaŃie– Un singur spooler– Un singur sistem de fişiere– Un singur gestionar de ferestre
• Aplicabilitate– InstanŃa unică a unei clase trebuie să fie accesibilă clienŃilor într-
un punct cunoscut– InstanŃa unică trebuie să fie extensibilă; clienŃii nu trebuie să îşi
modifice codul
IP7 Singleton (2)
• Structura
Singleton
-static uniqueInstance:-singletonData
+static Instance()+SingletonOperation()+GetSingletonData()
return uniqueInstance
IP7 Singleton (java)
public class Singleton { private static Singleton instance = null; private Singleton() {…}public static Singleton getInstance () {
if( instance == null ) { instance = new Singleton();
} return instance;
} public void operation() { … }
}
public class Client { public static void main( String arg[] ) {
try { Singleton instance = Singleton. getInstance (); instance.operation();
} catch( Exception e ) { e.printStackTrace();
}
} }
IP7 Singleton (C++)
class Singleton { private:
static Singleton* singleton;Singleton () {…}
public: static Singleton* instance() {
if( singleton == 0 ) { singleton = new Singleton();
} return singleton;
}; void operation() {…}
};
Singleton* Singleton::singleton = 0;
int main() { Singleton* singleton = Singleton::instance(); singleton->operation();return 0;
}
IP7 Singleton (C++)
Singleton Pattern: A review and analysis of existing C++ implementations
http://www.codeproject.com/cpp/singleton.asp
IP7 Factory Method / Metodă fabrică
• Scop: Defineşte o interfaŃă pentru crearea unui obiect, dar lasă în sarcina subclaselor alegerea tipului acestuia.
• MotivaŃie– O bibliotecă foloseşte clase abstracte pentru a defini şi
menŃine relaŃii între obiecte.– Un tip de responsabilitate este crearea de astfel de
obiecte.– Biblioteca ştie când trebuie creat un obiect, dar nu şi
ce tip de obiect trebuie creat (acesta este specific aplicaŃiei care foloseşte biblioteca)
IP7 Factory Method (2)
• MotivaŃie - exemplu
Framework
Application
Document
Application
+CreateDocument()+NewDocument()
MyDocument
MyApplication
+CreateDocument()
Document* doc =CreateDocument();
// add doc to container
return newMyDocument()
IP7 Factory Method (3)
• Aplicabilitate– Când o clasă nu poate anticipa tipul obiectelor care
trebuie să le creeze– Când o clasă vrea ca subclasele să specifice tipul
obiectelor de creat
• Structura
ProductCreator
+FactoryMethod()+AnOperation()
ConcreteCreator
+FactoryMethod()ConcreteProduct
product =FactoryMethod()
return newConcreteProduct
IP7 Factory Method (java)
public interface Product { … }
public abstract class Creator { public void anOperation() {
Product product = factoryMethod(); } protected abstract Product factoryMethod();
}
public class ConcreteProduct implements Product { … }
public class ConcreteCreator extends Creator { protected Product factoryMethod() {
return new ConcreteProduct(); }
}
public class Client { public static void main( String arg[] ) {
Creator creator = new ConcreteCreator(); creator.anOperation();
}}
IP7 Factory Method (C++)
class Product { };
class Creator { protected:
virtual Product* factoryMethod() = 0; public:
void anOperation() { Product* product = factoryMethod(); /** * Do some things with the Product object. */ delete product;
}; };
class ConcreteProduct: public Product { };
class ConcreteCreator: public Creator { protected:
virtual Product* factoryMethod() { return new ConcreteProduct();
}; };
IP7 Factory Method (C++)
int main() {
/** * Instantiate a Creator object. */
Creator* creator = new ConcreteCreator();
/** * Call the operation which uses a factory metho d. */ creator -> anOperation();
/** * Clean-up. */
delete creator;
};
IP7 Strategy / Strategie
• Scop: Se defineşte o familie de algoritmi; se încapsulează fiecare mebru; algoritmii se facinterschimbabili.
• MotivaŃie
Sorter
+MethodWithSort()
Sort
+Sort()
QuickSort NaiveSortHeapSortsort->Sort()
IP7 Strategy (2)
• Aplicabilitate– Multe clase înrudite diferă doar prin comportament– Se folosesc diverse variante ale unui algoritm– Algoritmii folosesc date irelevante pentru client– O clasă defineşte comportamente multiple, definite de
condiŃii gardă la începutul metodelor.
• Structură
Context
+ContextInterface()
Strategy
+AlgorithmInterface()
ConcreteStrategyA ConcreteStrategyB
IP7 Strategy (java)
// Abstract Strategy
class abstract class Strategy{
public abstract void algorithmInterface();
}
// ConcreteStrategyA
class class ConcreteStrategyA extends Strategy{
public void algorithmInterface(){
System.out.println("ConcreteStrategyA algorithm is used now");
}
}
// ConcreteStrategyB class
class ConcreteStrategyB extends Strategy{
public void algorithmInterface(){
System.out.println("ConcreteStrategyB algorithm is used now");
}
}
IP7 Strategy (java)
class Context{ //Default Algorithm private Strategy strategy = new ConcreteStrategyA(); public void changeStrategy(Strategy newStrategy){
strategy=newStrategy; } public void getResult(){
strategy. algorithmInterface(); }
} //Client class public class Client{
public static void main(String args[]){ Context context=new Context(); context.getResult(); context.changeStrategy(new ConcreteStrategyB()); context.getResult();
} }
IP7 Decorator
• Scop– Obiectelor li se pot ataşa respnsabilităŃi în mod dinamic.– Alternativă flexibilă la derivare pentru extinderea funcŃionalităŃii
• MotivaŃie
IP7 Decorator (2)
• Aplicabilitate– Adăugarea responsabilităŃilor în mod dinamic şi transparent– Retragerea responsabilităŃilor– Atunci când derivarea devine nepractică
• Structura
Component
+Operation()
ConcreteComponent Decorator
+Operation()
ConcreteDecoratorA
-addedState
+Operation()
ConcreteDecoratorB
+Operation()+AddedBehavior()
component->Operation()
Decorator::Operation();AddedBehavior();
IP7 Decorator (java)
//VisualComponent
class class VisualComponent{
public VisualComponent(){};
public void draw(){};
public void resize(){};
}
//Decorator abstract
class Decorator extends VisualComponent{
private VisualComponent comp;
Decorator(){};
Decorator(VisualComponent comp){ this.comp=comp; }
public void draw(){
comp.draw();
//Implement your code here
}
public void resize(){ //Implement your code here }
}
IP7 Decorator (java)
//BorderDecoratorclass BorderDecorator extends Decorator{
private int width;
BorderDecorator(VisualComponent comp, int borderWidth ){ //Implement your code here width=borderWidth;
}
public void draw(){ super.draw(); drawBorder(width);
}
public void drawBorder(int width){ System.out.println("This is an example of Decorator design
pattern"); //Implement code here
} }
IP7 Decorator (java)
public class Client{
public static void main(String args[]){
//Create an instance of VisualComponentVisualComponent comp=new VisualComponent();
//Pass this instance to BorderDecoratorcomp=new BorderDecorator(comp,5);
comp.draw();
}
}
Alternativ:VisualComponent comp=
new BorderDecorator(new VisualComponent(),5)
IP7 Composite / Amestec
• Scop– Se doreşte gruparea obiectelor în structuri arborescente
pentru a reprezenta relaŃii de tip parte-întreg.– Obiectele şi grupurile de obiecte sunt tratate uniform.
• MotivaŃie
IP7 Composite (2)
• Aplicabilitate– Reprezentarea relaŃiei parte-întreg– Ignorarea diferenŃei dintre obiecte individuale şi grupurile de
obiecte
• StructuraClient Component
+Operation()+Add(c:Component)
+Remove(c:Component)+GetChild(i:int)
Leaf
+Operation()
Composite
+Operation()
for all c:child c->Operation()
child
IP7 Composite (java)
public interface Component {
void operation();
void add( Component component );
boolean remove( Component component );
Component getChild( int index );
}
public class Leaf implements Component {
public void operation() { }
public void add( Component component ) { }
public boolean remove( Component component ) {
return false;
}
public Component getChild( int index ) {
return null;
}
}
IP7 Composite (java)
public class Composite implements Component {
private Vector children = new Vector();
public void operation() {
int i;
for( i = 0; i < children.size(); ++i ) {
Component component = (Component)children.elementAt(i ); component.operation();
}
}
public void add( Component component ) { children.addElement( component );
}
public boolean remove( Component component ) {
return children.removeElement( component );
}
public Component getChild( int index ) {
return (Component) children.elementAt(index);
}
}
IP7 Composite (java)
public class Client {
public static void main( String arg[] ) {
Component composite = new Composite();
Component leaf1 = new Leaf();
Component leaf2 = new Leaf();
composite.add( leaf1 );
composite.add( leaf2 );
composite.operation();
}
}
IP7 Iterator
• Scop: Oferă o modalitate de a accesa obiecte agregate în mod secvenŃial fără a cunoaşte modul de agregare.
• MotivaŃie
List
ListIterator
+First()+Next()
+IsDone()+CurrentItem()
IP7 Iterator (2)
• MotivaŃie (2)
Container
+CreateIterator()+Append(i:Item)
List Vector
Iterator
+First()+Next()
+IsDone()+CurrentItem()
ListIterator
+First()+Next()
+IsDone()+CurrentItem()
VectorIterator
Client
IP7 Iterator (3)
• Structura
Aggregate
+CreateIterator()
ConcreteAggregate
+CreateIterator()
return newConcreteIterator(this)
ConcreteIterator
Iterator
+First()+Next()
+IsDone()+CurrentItem()
Client
IP7 Iterator (java)
public interface Iterator {
Object first() throws IndexOutOfBoundsException;
Object next() throws IndexOutOfBoundsException;
boolean isDone();
Object currentItem() throws IndexOutOfBoundsExcepti on;
}
public interface Aggregate {
Iterator createIterator();
}
public class ConcreteAggregate implements Aggregate {
public Vector storage = new Vector();
public Iterator createIterator() {
return new ConcreteIterator( this );
}
}
IP7 Iterator (java)
public class ConcreteIterator implements Iterator { private ConcreteAggregate aggregate; private int index = 0;
public ConcreteIterator( ConcreteAggregate aggregate ) { this.aggregate = aggregate;
}
public Object first() throws IndexOutOfBoundsExcept ion { Object object = null; if( !aggregate.storage.isEmpty() ) {
index = 0; object = aggregate.storage.firstElement();
} else { throw new IndexOutOfBoundsException();
} return object;
}
IP7 Iterator (java)
public Object next() throws IndexOutOfBoundsExcepti on {
Object object = null;
if( index + 1 < aggregate.storage.size() ) {
index += 1;
object = aggregate.storage.elementAt(index);
} else {
throw new IndexOutOfBoundsException();
}
return object;
}
IP7 Iterator (java)
public boolean isDone() { boolean result = false; if( aggregate.storage.isEmpty() ||
index == aggregate.storage.size() - 1 ) { result = true;
} return result;
}
public Object currentItem() throws IndexOutOfBounds Exception { Object object = null; if( index < aggregate.storage.size() ) {
object = aggregate.storage.elementAt( index ); } el se {
throw new IndexOutOfBoundsException(); } return object;
} }//class
IP7 Iterator (java)
public class Client {
public static void main( String arg[] ) {
Aggregate aggregate = new ConcreteAggregate();
Iterator iterator = aggregate.createIterator();
for(iterator.first(); !iterator.isDone(); iterator.next()) {
Object currentItem = iterator. currentItem();
/** * Process currentItem */
}
}
}
IP7 Template Method / Metodă şablon
• Scop: Se defineşte scheletul unui algoritm într-o metodă, lăsând implementarea paşilor algoritmului în seama subclaselor.
• MotivaŃie
void Application::OpenDocument(string& name){
if (!CanOpenDocument(name))return;
Document* pDoc = CreateDocument();if (pDoc == 0)
return;m_docs.add(pDoc);InitializeOpenDocument(pDoc);pDoc->Read();
}
Document
+Read()
Application
+CreateDocument()+CanOpenDocument()
+InitializeOpenDocument()+OpenDocument()
MyApplication
+CanOpenDocument()+InitializeOpenDocument()
+CreateDocument()
MyDocument
+Read()
IP7 Template Method (2)
• Aplicabilitate– Implementarea structurii fixe a unui algoritm, lăsând
clasele derivate să implementeze funcŃionalitatea care variază
– Când funcŃionalitatea comună a unor clase este relocată într-o clasă de bază
• Structură AbstractClass
+TemplateMethod()+PrimitiveOperation1()+PrimitiveOperation2()
ConcreteClass
+PrimitiveOperation1()+PrimitiveOperation2()
PrimitiveOperation1()...PrimitiveOperation2()
IP7 Template Method
public abstract class AbstractClass {
public void templateMethod() {
primitiveOperation1();
primitiveOperation2();
}
protected abstract void primitiveOperation1();
protected abstract void primitiveOperation2();
}
public class ConcreteClass extends AbstractClass {
protected void primitiveOperation1() { }
protected void primitiveOperation2() { }
}