myCSharp.de - DIE C# und .NET Community
Willkommen auf myCSharp.de! Anmelden | kostenlos registrieren
 
 | Suche | FAQ

» Hauptmenü
myCSharp.de
» Startseite
» Forum
» FAQ
» Artikel
» C#-Snippets
» Jobbörse
» Suche
» Regeln
» Wie poste ich richtig?
» Forum-FAQ

Mitglieder
» Liste / Suche
» Wer ist wo online?

Ressourcen
» openbook: Visual C#
» openbook: OO
» Microsoft Docs

Team
» Kontakt
» Übersicht
» Wir über uns

» myCSharp.de Diskussionsforum
Du befindest Dich hier: Community-Index » Diskussionsforum » Knowledge Base » Artikel » [Artikel] Entwurfsmuster: Decorator
Letzter Beitrag | Erster ungelesener Beitrag Druckvorschau | Thema zu Favoriten hinzufügen

Antwort erstellen
Zum Ende der Seite springen  

[Artikel] Entwurfsmuster: Decorator

 
Autor
Beitrag « Vorheriges Thema | Nächstes Thema »
pro pro ist männlich
myCSharp.de-Mitglied

Dabei seit: 01.11.2006
Beiträge: 216
Entwicklungsumgebung: VS.NET 2008
Herkunft: Schweiz


pro ist offline

[Artikel] Entwurfsmuster: Decorator

Beitrag: beantworten | zitieren | editieren | melden/löschen       | Top

Einführung:

Wiedermal darf ich ein Entwurfsmuster kennenlernen. Diesmal ist es das Decorator Pattern. Um es vorweg zu nehmen, bei der folgenden kleinen “Vorstellung” des Decoratorpattern, wird das Entwurfsmuster nicht in Kombination mit dem Factory Pattern aufgezeigt. Es geht einzig um das Decorator Pattern.

Das Decoratorpattern kann man in einem UML Klassendiagramm so aufzeichnen :



Defintion:

Das Decoratormuster fügt einem Objekt dynamisch zusätzliche Verantwortlichkeiten hinzu. Dekorierer bieten eine flexible Alternative zur Ableitung von Unterklassen zum Zweck der Erweiterung der Funktionalität.

Zusammenfassung:

Die Definition sagt nichts anderes aus, als dass die oben aufgezeichneten Komponenten dynamisch erweitert (oder eben dekoriert) werden können. Dynamisch bedeutet hier, dass man die Funktionalitäten zur Laufzeit beliebig hinzufügen kann.

Beispiel - Ein Menü Dekorierer :-)

Das Beispiel hat nichts mit dem Programmieralltag zu tun. Jedoch eigenen sich Menü’s extrem zum dekorieren.

Es gibt in einem Restaurant zwei Menues (Menü 1 und Menu 2). Ein Kunde kann aber diese Menues beliebig erweitern wie er will. D.h. er kann zu einem Menu noch ein Hamburger, Pommes Frites oder Nuggets bestellen. Dies bedeutet, dass er die beiden Menues um die Zutaten beliebig erweitern (oder eben “dekorieren” ) kann.

Das Klassendiagramm dieser Menues sieht dann auf das Decoratormuster umgesetzt so aus :



Implementierung (auf Restaurant - Beispiel bezogen)

Abstrakte Komponenten Klasse (Menu) :

C#-Code:
/// <summary>
/// Abstrakte Komponente (Menu)
/// Alle Komponenten müssen von dieser "Hauptkomponente"
///erben, damit sie dekoriert werden können.
/// </summary>
public abstract class Menu
{
/// <summary>
/// Feld, welches durch das ganze Decoratormuster
///hindurchgezogen wird.
/// In diesem Fall Description. Wird in jeder
/// Komponente bzw. Dekorierer
/// anders sein
/// </summary>
protected string description = "menu";

/// <summary>
/// Property, welche die Unterklassen benötigen,
/// um auf die Oberklasse / Superklasse /
///Baseklasse zugreifen zu können
/// </summary>
public abstract string Description { get; }

/// <summary>
/// Zu überschreibende Methode Preis, welche
/// durch die Komponenten statisch, bzw. durch die Dekorierer
/// dynamisch gesetzt werden
/// </summary>
/// <returns>Preis</returns>
public abstract double Preis();
}

Eine konkrete Komponente (Menu_1):

C#-Code:
/// <summary>
/// Komponente 1
/// </summary>
public class Menu_1 : Menu
{
/// <summary>
/// Konstruktor der Komponente
/// </summary>
public Menu_1()
{
this.description = "Menu_1";
}

/// <summary>
/// Überschriebene Methode, der
///Abstrakten- bzw. Hauptkomponente
/// (statischer Preis der Komponente, ohni "Dekorierungen";)
/// </summary>
/// <returns>Preis</returns>
public override double Preis()
{
return 11.00;
}

/// <summary>
/// Überschriebens Description Property
/// </summary>
public override string Description
{
get { return this.description; }
}

Abstrakter Dekorierer (Erbt von Menu, da das dekorierte Objekt schlussendlich auch wieder eine Komponente ist)

C#-Code:
/// <summary>
/// Hauptdekorierer
/// (Alle konkreten Dekorierer werden
///von diesem Dekorierer ableiten)
/// </summary>
public abstract class MenuDecorator : Menu
{
/// <summary>
/// Property oder Methode, welche Dekoriert werden soll
/// </summary>
public override string Description {
get { return this.description; }
}

Konkreter Dekorierer (in diesem Fall die Hamburger, welche zum Menu gehören)

C#-Code:
/// <summary>
/// Dekorierer, welcher Hamburger zur Komponente hinzufügt
/// </summary>
public class HamburgerDecorator : MenuDecorator
{
/// <summary>
/// Objekt, welches dekoriert werden soll
/// </summary>
private Menu menu;

/// <summary>
/// Konstrukter des Dekorierers
/// </summary>
public HamburgerDecorator(Menu menu)
{
this.menu = menu;
}

/// <summary>
/// Beschreibung, welche durch den Dekorierer
/// dekoriert wird
/// (zur Menu Description kommt noch der dekorierte Text)
/// </summary>
public override string Description
{
get { return menu.Description + " + Hamburger"; }
}

/// <summary>
/// Dekorierter Preis
/// (da das Objekt um "Hamburger" erweitert wurde,
/// muss natürlich auch der Preis erhöht werden)
/// </summary>
/// <returns>Preis</returns>
public override double Preis()
{
return 2.50 + menu.Preis();
}
}

Verwendung der Dekorierer

C#-Code:
/// <summary>
/// Main - Methode
/// </summary>
///
static void Main(string[] args)
{
//Ich möchte ein Menu_1 ohne weitere Zutaten ( 11.00 )
Menu menu = new Menu_1();
Console.ForegroundColor = ConsoleColor.Cyan;
Console.WriteLine("Ich möchte ein Menu_1 ohne weitere Zutaten"+
";( 11.00 )...";);
Console.WriteLine("Beschreibung : "
+ menu.Description + " / Preis : " + menu.Preis());
Console.WriteLine();

Console.ForegroundColor = ConsoleColor.Yellow;

//Ich möchte nun ein Menu_1 mit Hamburger
//(Achtung : menu ist bereits ein Menu_1 Objekt!
//Darum keine Menu_1 Instanzierung notwendig!)

//-- Hamburger hinzufügen ( + 2.50 )
menu = new HamburgerDecorator(menu);

Console.WriteLine("Ich möchte zu meinem" +
"bestellten Menu_1 (11.00) ein zusätzlicher" +
" Hamburger (2.50)..";);
Console.WriteLine("Beschreibung : "
+ menu.Description + " / Preis : " + menu.Preis());
Console.WriteLine();

Console.ForegroundColor = ConsoleColor.Cyan;

//Ich möchte nun ein Menu_1 mit
//zusätzlichem Hamburger und Chicken Nuggets
//(Achtung : menu ist bereits ein Menu_1 mit Hamburger!)

//--Hamburger hinzufügen ( + 2.50 )
menu = new HamburgerDecorator(menu);

//--Nuggets hinzufügen ( + 1.50 )
menu = new NuggetsDecorator(menu);

Console.WriteLine("Ich möchte nun zu meinem" +
" Menu_1 einen zusätzlichen Hamburger (2.50) und" +
"Chicken Nuggets (1.50)...";);
Console.WriteLine("Beschreibung : "
+ menu.Description + " / Preis : " + menu.Preis());
Console.WriteLine();

//Ich möchte nun ein Menu_2 mit Pommes und Nuggets
//menu wird durch die Neuinstanzierung überschrieben!!

//--Menu_2 erstellen (9.00)
menu = new Menu_2();

//--Pommes hinzufügen ( + 3.00)
menu = new PommesDecorator(menu);

//--Nuggets hinzufügen ( + 1.50)
menu = new NuggetsDecorator(menu);

Console.ForegroundColor = ConsoleColor.Yellow;

Console.WriteLine("Ich möchte nun ein neues " +
"Menu_2 (9.00) mit Pommes (3.00) und Nuggets (1.50)...";);
Console.WriteLine("Beschreibung : "
+ menu.Description + " / Preis : " + menu.Preis());

Console.WriteLine();

Console.WriteLine("Press <enter> to exit...";);</enter>

Console.ReadLine();

}

Das Schlussresultat der Beispielverwendung der Decorator sieht dann so aus:



Das Projekt als Download ist angehängt (=> VS05 Solution).

Weiterführende Links:

>  http://en.wikipedia.org/wiki/Decorator_pattern
>  http://exciton.cs.rice.edu/JavaResources...atorPattern.htm
>  http://www.onjava.com/pub/a/onjava/2003/02/05/decorator.html
>  http://www.informit.com/articles/article...=31350&seqNum=1
>  http://www.codeproject.com/info/search.a...ecorator&sbo=kw


Schlagwörter: Decorator, Pattern, Entwurfsmuster


Dateianhang:
unknown DecoratorPattern.rar (20,26 KB, 909 mal heruntergeladen)

Dieser Beitrag wurde 3 mal editiert, zum letzten Mal von pro am 18.12.2007 20:36.

18.12.2007 20:31 E-Mail | Beiträge des Benutzers | zu Buddylist hinzufügen
Baumstruktur | Brettstruktur       | Top 
myCSharp.de | Forum Der Startbeitrag ist älter als 11 Jahre.
Der letzte Beitrag ist älter als 11 Jahre.
Antwort erstellen


© Copyright 2003-2019 myCSharp.de-Team | Impressum | Datenschutz | Alle Rechte vorbehalten. | Dieses Portal verwendet zum korrekten Betrieb Cookies. 15.10.2019 08:57