Klassen erweitern – Vererbung

In der Physik sind häufig Vierer–Vektoren (=Lorentz–Vektor) gefragt, d.h. Dreier–Vektoren erweitert um Zeit bzw. Energie–Komponente. Mögliche LorentzVektor Klasse:

 class MyLVector {
 private:        // coordinates, hidden
   double t;   double x;   double y;   double z;
 public:  
   MyLVector();// The default constructor
   MyLVector(double c0, double c1, double c2, double c3);// Other constructor
   // methods:
   double Length();  //   get length of vector
   double T();
   double X();
   double Y();
   double Z();
   MyLVector Add( MyLVector  p ) ;  // add two vectors
   double Angle(  MyLVector  p );  // angle between  two vectors
   double Mass() ;  //   get mass of 4-vector
 };


Viele Gemeinsamkeiten mit My3Vector und ein paar Erweiterungen

Design Prinzip Code-Reuse statt cut&paste !


Also vielleicht besser My3Vector in MyLVector benutzen:

 class MyLVector {
 private:        // coordinates, hidden
   double t;
   My3Vector vec3;  // My3Vector as private member
 public:  
   MyLVector();// The default constructor
   MyLVector(double c0, double c1, double c2, double c3);// Other constructor
   // methods:
   double Length();  //   get length of vector
   double T();
   double X();
   double Y();
   double Z();
   MyLVector Add( MyLVector p );  // add two vectors
   double Angle(  MyLVector p );  // angle between  two vectors
   //   ....
 };


\bgroup\color{green}\ensuremath{\Rightarrow}\egroup LorentzVektor enthält DreierVektor: "has-a" relationship (Aggregation).


// implementation
// Constructor
MyLVector::MyLVector(double c0, double c1, double c2, double c3) :
  vec3(c1, c2, c3), t(c0) // special initialization syntax 
{}

double MyLVector::Angle( MyLVector p )
{
  return( vec3.Angle(p.vec3)); // re-use code
}
double MyLVector::X()
{
  return( vec3.X() ); // re-use code
}

Im Prinzip ok, allerdings viele stumpfsinnige Mapping–Funktionen von DreierVektor auf ViererVektor nötig.


3. Möglichkeit: Vererbung

ViererVektor   ist   DreierVektor mit ein paar Ergänzungen ....


#include "My3Vector.h" // My3Vector declarations
class MyLVector : public My3Vector { // inherit from My3Vector
 private:        
   double t;
 public:  
   MyLVector();// The default constructor
   MyLVector(double c0, double c1, double c2, double c3);// Other constructor
   // methods:
   double Mass();  //   get mass of 4-vector
   double Mass( MyLVector p);  //   get mass of two 4-vector
 };
// implementation
MyLVector::MyLVector(double c0, double c1, double c2, double c3) :
  My3Vector(c1, c2, c3), t(c0) // special initialization syntax 
{}
 double MyLVector::Mass() // Method for mass:
 {
   // caution: direct access to My3Vector x,y,z doesn't work with private !
   return( sqrt( t*t - x*x - y*y - z*z ) ); 
 }

Jetzt übernimmt bzw. erbt MyLVector alle Funktionen von My3Vector, z.B. Winkelberechnung funktioniert sofort:
  MyLVector c(1.000001,1.,0.,0.), d(2.,1.,1.,0.);
  c.Angle(d);

Falls Methode geändert werden muss, z.B. MyLVector::Add, entsprechend neu implementieren, bei c.Add(d) wird dann die MyLVector Version benutzt.


Vererbung ( "is-a" relationship) bedeutet alle Eigenschaften und Funktionen einer Grund-Klasse ( base class) in eine weitere Klasse ( derived class) zu übernehmen. Daraus ergibt sich eine enorme Erweiterung der Funktionalität. Ausgehend von vorhandenen, simplen Grundklassen können relativ leicht neue Klassen abgeleitet werden, ohne jedesmal diesselben grundlegenden Funktionen neu zu implementieren.

Allerdings: Vererbung nicht übertreiben, nicht immer sinnvoll, im Zweifelsfall Aggregation verwenden.

Bei Verwendung von Polymorphismus (nächster Kurs ...) ist vor allem konsistentes Verhalten wichtig bei Vererbung, weniger die Funktionalität.


Weiteres zu Vererbung: