====== construct ====== ===== Kurzconstructor ===== Point contains { x, y is int; construct( x, y ); } x und y sind bekannt, sie sind vom Typ her int, also ist das ein Point(int, int)-Konstruktor. Die Übergaben werden direkt ins neue Objekt kopiert. Im Idealfall läuft die Konstruktion so inline ab. ===== Default Argumente ===== Defaultargumente werden wie in C mit der Zuweisung erledigt. Point contains { x, y is int; construct( x:0, y:0 ); construct( x = 0 as int, y = 0 as int ) := // hier sind x und y neue Konstanten, hier sollte eine Warning erfolgen { .x : x; .y : y; } construct( x is 0 as int, y is 0 as int ) := // hier sind x und y neue Variablen { x +: 1; y +: 1; .x : x; .y : y; } } ===== Const-Objekte ===== Es ist zu überlegen, ob Objekte grundsätzlich Konstant zurückgegeben werden. So würde Point contains { x, y is int; construct( x, y ); } einen unveränderlichen Punkt zurückliefern. Damit wäre is eine reine Ableitung und verliert seine Bedeutung als mutable object. Wenn man auf 'class' geht könnte man mutable bzw. const einführen: Point is const/var class { x, y is int; construct( x, y ); } um sich für die komplette Klasse festzulegen. Legt man sich nicht fest, könnte man nach OOP von einer mutable class ausgehen und const Konstruktoren definieren: Point is class { x, y is int; construct( x, y ) const; } Da Genesys allerdings maximal restriktiv sein soll, könnnte man auch von einer konstanten Klasse per Default ausgehen: Point contains { x, y is int; construct( x, y ) var; } ===== construct as ===== Ein Konstruktor kann mit der as Anweisung Parameter gleich auf dem Zielspeicher initialisieren: Rect contains { Source is Point; // erstellt expliziten construct( Point ) Target is Point; // erstellt expliziten construct( Point ) construct( Point as Source, Point as Target ); construct( Source, Target ); }; Der Construktor schreibt die übergebenen Punkte direkt nach Source bzw. Target. Erlaubt sind ( Point, Point ), aber auch ( Rect::Source, Rect::Target ). Hier findet im ersten Konstruktor ein expliziter Aufruf von Rect::Source::construct( Point ), bzw. Rect::Target::construct( Point ) statt. Im 2. Konstruktor wird ebenfalls nur durchgereicht, als Eingangstyp wird allerdings Rect::Source, bzw. Rect::Target verlangt. ===== new construct as ===== Müssen Berechnungen durchgeführt werden, so können temporäre Objekte mit as - Parametern verhindert werden. Sie werden direkt im neuen Objekt erstellt: Statt: Point contains { XOffset is int; YOffset is int; construct( XOffset, YOffset ) }; offset as int : 4711; x as int : offset + 10; y as int : offset + 20; p as Point ptr : new( x, y ); oder Point contains { XOffset is int; YOffset is int; construct( XOffset, YOffset ) := print "Punkt ", XOffset$, "/", YOffset$, "konstruiert"; }; offset as int : 4711; p as Point ptr : new( XOffset, YOffset ) { XOffset : offset + 10; YOffset : offset + 20; } Im zweiten Fall wird das Objekt erzeugt und es gibt einen gültigen Konstruktor ( XOffset, YOffset ). Der Konstruktor besteht aus zwei Teilen: Dem Initialisierungsbereich: der Zuweisung von XOffset und YOffset, die vor der print-Anweisung initialisiert werden; und eben dem Anweisungsblock mit dem Print. ''new( XOffset, YOffset )'' stellt klar, welcher Konstruktor verwendet wird. Alle im Konstruktor genannten Variablen müssen initialisiert werden. Anschließend wird der Anweisungsblock des Konstruktors gerufen. Die Initialisierung wurde bereits vom Benutzer übernommen.