2016-03-18 5 views
-2

Ich habe eine abstrakte Klasse namens Form.Wie kann man einen Parameter eines abstrakten Datentyps haben?

class Shape{ 
public: 
    virtual const ColorRGB getColor() const; 
    virtual double rayIntersectionDistance(Ray r) = 0; 
}; 

Und jetzt habe ich die folgenden Klassen von Form abgeleitet.

  1. class Sphere: public Shape { //implementation goes here }
  2. class Plane: public Shape { //implementation goes here }

ich beide getColor implementiert haben() und rayIntersectionDistance (Ray r) Methoden innerhalb der beiden Klassen, mit zusätzlichen Methoden spezifisch für diese Klassen.

So, jetzt in einer anderen Klasse, genannt Szene, ich habe ein render() Methode, und es Prototyp ist:

void render(int width, int height, Shape s); 

Und das scheint zu nicht funktioniert, der Compiler beschwerde mich sagen:

error: cannot declare parameter 's' to be of abstract type 'Shape'

Wie kann ich dies geschehen lassen? Was wäre ein besserer Weg, dies zu erreichen?

Antwort

3

Wenn Sie einen Wert von Shape übergeben, wird eine Instanz von Shape übergeben. Aber Shape ist abstrakt, so dass eine Instanz nicht erstellt werden kann.

Übergeben Sie stattdessen einen Zeiger oder eine Referenz. const qualifizieren Sie sich, wenn das übergebene Objekt nicht geändert werden soll (wodurch auch die Übergabe von Objekten verhindert wird, die als const deklariert sind, da sie nicht geändert werden sollten).

void func(Shape &s); // define these functions as required 
void func2(Shape *s); 
void func3(const Shape &s); 

int main() 
{ 
     Sphere s; // assumed non-abstract 

     const Sphere s2; 

     func(s);  // will work 
     func2(&s); // ditto 

     func3(s); // okay 
     func3(s2); // okay 

     func(s); // rejected, as s2 is const 
} 

Edit:

Wie in den Kommentaren von Barry erwähnt, ist es auch möglich, intelligente Zeiger, wie std::unique_pointer<Shape> oder std::shared_pointer<Shape> passieren - und die kann von Wert übergeben werden. Das ist in der Praxis ungewöhnlich, wie von Richard Hodges erwähnt, obwohl es möglich ist. Tatsächlich kann jeder Typ übergeben werden, der einen Zeiger oder einen Verweis auf Shape verwaltet - vorausgesetzt, seine Konstruktoren (insbesondere der Kopierkonstruktor) implementieren entsprechendes Verhalten.

+3

'func4 (unique_ptr )', 'Fkt5 (Shared_ptr )', ... ;-) – Barry

+2

@barry fair zu sein, ein unique_ptr zu einem Unentschieden Funktion ungewöhnlich wäre bewegt vorbei. @Peter Ich würde wahrscheinlich 'func()' oder 'func2()' nicht ermutigen. viel zu nutzlos ... 'func3()' ist der eine. –

+0

@Barry - ja. Es ist auch möglich, einen beliebigen Typ zu übergeben, der einen Zeiger oder einen Verweis auf 'Shape' enthält - einschließlich der intelligenten Zeigertypen, wie Sie es nennen -, solange dieser Typ seinen Status entsprechend verwaltet. – Peter

Verwandte Themen