2016-08-08 55 views
-1

Ich habe meine Getränk Klasse, die einige Getter/Setter hat, um mit der Größe des Getränks zu arbeiten. Dieses Programm hat mit dem Decorator-Muster zu tun, also möchte ich das Verhalten einiger gleich genannter Methoden kombinieren.make abstract eine Methode mit Körper zum Überschreiben

Meine Absicht ist es, eine Methode mit Körper zu haben, die mir erlaubt, die Größe des Getränks zu bekommen, aber dann möchte ich in der Lage sein, dieses Verhalten auf Unterklassen zu überschreiben.

Zusammengefasst möchte ich eine Methode, die:

  • wenn nicht außer Kraft gesetzt, ebenso wie die Methode
  • wenn außer Kraft gesetzt in der übergeordneten Klasse verhält, verhält sich wie es
  • codiert

Was Ich habe eine Methode namens getSizeOfBeverage erstellt, die sich wie meine "alten" getSize tat, und machte die getSize "n ew "methode abstract, damit ich sie überschreiben kann, aber ich möchte eine Lösung, die keinen neuen Methodennamen impliziert.

Hier ist mein Code:

using System; 

namespace Decorator 
{ 
    class Program 
    { 
     static void Main(string[] args) 
     { 
      Beverage beverage = new Espresso("small"); 
      beverage = new Whip(beverage); 
      Console.WriteLine(beverage.getDescription() + " $" + beverage.cost()); 
     } 
    } 

    abstract class Beverage 
    { 
     private string description; 
     private string size; 

     public Beverage() 
     { 
     setDescription("Unknown beverage"); 
     } 

     public double getCost() 
     { 
     return cost(); 
     } 

     public abstract double cost(); 

     public abstract string getDescription(); 

     public void setDescription(string desc) 
     { 
     description = desc; 
     } 

     public string getSizeOfBeverage() 
     { 
     return size; 
     } 

     public abstract string getSize(); 

     public void setSize(string sz) 
     { 
     size = sz; 
     } 
    } 

    class Espresso : Beverage 
    { 
     public Espresso(string sz) 
     { 
     setSize(sz); 
     setDescription("Espresso"); 
     } 

     public override double cost() 
     { 
     return 1.9; 
     } 

     public override string getDescription() 
     { 
     return getDescription(); 
     } 

     public override string getSize() 
     { 
     return getSizeOfBeverage(); 
     } 
    } 

    abstract class CondimentDecorator : Beverage 
    { 
     public abstract override string getSize(); 
    } 

    class Whip : CondimentDecorator 
    { 
     private Beverage beverage; 

     public Whip(Beverage bv) 
     { 
     beverage = bv; 
     } 

     public override double cost() 
     { 
     if (getSize() == "small") 
     { 
      return 0.1 + beverage.cost(); 
     } 
     else if (getSize() == "medium") 
     { 
      return 0.15 + beverage.cost(); 
     } 
     else 
     { 
      return 0.2 + beverage.cost(); 
     } 
     } 

     public override string getDescription() 
     { 
     return beverage.getDescription() + ", whip"; 
     } 

     public override string getSize() 
     { 
     return beverage.getSizeOfBeverage(); 
     } 
    } 
} 

Antwort

4

wenn nicht außer Kraft gesetzt, verhält sich genauso wie die Methode in der übergeordneten Klasse, wenn

außer Kraft gesetzt, verhält sich wie es

Jede codiert virtual Methode funktioniert wie folgt:

Wenn es außer Kraft gesetzt wird, es verhält wie es codiert, wenn nicht nur als Methode in der Klasse Eltern verhält

Aus der Dokumentation für virtual

Das virtuelle Schlüsselwort verwendet wird, eine Methode, eine Eigenschaft zu ändern, Indexer oder Event-Deklaration und erlauben Sie es in einer abgeleiteten Klasse überschrieben werden. Beispielsweise kann dieses Verfahren durch jede Klasse außer Kraft gesetzt wird, dass erbt es:

und abstract

Wenn eine Instanz Verfahren Deklaration enthält einen abstrakten Modifikator, das Verfahren das ist eine abstrakte Methode sein, . Obwohl eine abstrakte Methode implizit auch eine virtuelle Methode ist, kann sie den Modifikator nicht virtuell haben. Eine abstrakte Methodendeklaration führt eine neue virtuelle Methode ein, bietet jedoch keine Implementierung dieser Methode. Stattdessen müssen nicht abstrakte abgeleitete Klassen ihre eigene Implementierung durch Überschreiben dieser Methode bereitstellen. Da eine abstrakte Methode keine tatsächliche Implementierung bereitstellt, besteht der Methodenhauptteil einer abstrakten Methode einfach aus einem Semikolon.

Sehen Sie den Unterschied zwischen virtual and abstract methods in C#