Lösung

Werbung
Universität der Bundeswehr
Fakultät für Informatik – Institut 2
Priv.-Doz. Dr. Lothar Schmitz
FT 2006
Übungsblatt 2
Lösungsvorschlag
Objektorientierte Programmierung
24. 04. 2006
Lösung 5 (Vererbung - Trace (Klausur FT 2001))
a)
b) Die Objekte können von Unfug und Schrott erzeugt werden.
c) Die nummerierten Zeilen waren gefordert. Die Reihenfolge von schrott.was() und unfug.was() ist
natürlich frei wählbar.
Objekte erzeugen (nicht in Lösung gefordert):
-->>new Unfug(200)
Mehr Unfug:
Die 47
-->>new Schrott(100)
Mehr Unfug:
Eine 47
Mehr Schrott:
Eine 47
-->>Outputs:
-->>schrott.was():
Mehr Unfug:
Eine 47
Mehr Schrott:
Eine 47
Verschiedener Schrott
JaJa
Eine 11
Die 11
-->>unfug.was():
JaJa
Die 47
(Zeile
(Zeile
(Zeile
(Zeile
(Zeile
(Zeile
(Zeile
(Zeile
1)
2)
3)
4)
5)
6)
7)
8)
(Zeile 9)
(Zeile 10)
1
Lösung 6 (GEO Paket: UML-Klassendiagramm)
a)
b) Die toString-Methode einer Klasse wandelt die Objekte in Strings um. Da innerhalb eines Objektes wiederum andere Objekte enthalten sind (Aggregation/Composition), ist es eventuell notwendig, auch diese in
den String einzugliedern. Beispielsweise sind bei einer Strecke Anfangs- und Endpunkt als Koord-Objekte
gespeichert. Somit müssen diese auch in einen String umgewandelt werden, wozu die toString-Methode
dieser Objekte genutzt wird. Je nach Schachtelung der Objekte kann der Aufruf der toString-Methode
eines Objektes viele rekursiv geschachtelte Aufrufe anderer toString-Methoden nach sich ziehen.
c) Vererbung wird in der GEO-Software genutzt, um eine Hierarchie geometrischer Figuren aufzubauen. Der
Kopf der Hierarchie in GEO ist die Klasse Figur (die wiederum von java.lang.Object abgeleitet
ist). Es wird vorausgesetzt, dass jede Figur an einem Ort (Attribut ort) zu finden ist. Punkt und Linie
sind direkte Unterklassen von Figur. Sie erben die nicht-privaten Anteile (hier: alle Methoden). In beiden Klassen werden je nach Notwendigkeit die Methoden clone, toString und equals überschrieben,
da beide Klassen spezialisierte geometrische Figuren beschreiben. Weiterhin werden je nach Klasse weitere
2
Methoden hinzugefügt. Die Klassenhierarchie pflanzt sich unter Punkt und Linie fort.
Die Klasse Koord wird nicht vererbt, sondern durch Figur und Linie genutzt.
Lösung 7 (GEO-Paketergänzung: Inkreis)
Die Ausführung von Umkreis.main() ergibt:
d1:Dreieck (-2.0,-4.0)(4.0,-2.0)(-2.0,4.0)
Berechne Kreis durch die Punkte des Dreiecks d1
s3 von Punkt1 nach Punkt2:
Strecke von (-2.0,-4.0) bis (4.0,-2.0)
s4 von Punkt1 nach Punkt3:
Strecke von (-2.0,-4.0) bis (-2.0,4.0)
Mittelsenkrechte von s3: Gerade durch (1.0,-3.0) und (-1.0,3.0)
Mittelsenkrechte von s4: Gerade durch (-2.0,0.0) und (-10.0,0.0)
Schnittpunkt der Mittelsenkrechten: (0.0,0.0)
Radius = Abstand von Punkt1 zu Schnittpunkt: 4.47213595499958
Ergebnis ist der Umkreis des Dreiecks: Kreis um (0.0,0.0) mit Radius 4.47213595499958
Winkel.java:
class Winkel {
// Daten
private Punkt p1, p2, p3;
// Methoden zur Kapselung
private void setP1(Punkt p1) {
this.p1 = p1;
}
public Punkt getP1() {
return this.p1;
}
private void setP2(Punkt p2) {
this.p2 = p2;
}
public Punkt getP2() {
return this.p2;
}
private void setP3(Punkt p3) {
this.p3 = p3;
}
public Punkt getP3() {
return this.p3;
}
//Konstruktor
Winkel(Punkt p1, Punkt p2, Punkt p3) {
setP1(p1);
setP2(p2);
setP3(p3);
}
// öffentliche Methoden
public Gerade winkelhalbierende() {
// Idee: Vectoraddition: (p2 -> p1) + (p2 -> p3) ergibt
3
// Parallelogramm und neuen Punkt p4
// Somit ist Winkelhalbierende die Gerade durch p1 und p4
Koord vectorP2_P1 = p1.getOrt().minus(p2.getOrt());
Koord vectorP2_P3 = p3.getOrt().minus(p2.getOrt());
// normieren:
vectorP2_P1 = vectorP2_P1.mal(1/vectorP2_P1.betrag());
vectorP2_P3 = vectorP2_P3.mal(1/vectorP2_P3.betrag());
System.out.println(vectorP2_P1);
System.out.println(vectorP2_P3);
// Parallelogram
Koord p4 = vectorP2_P1.plus(vectorP2_P3);
Gerade g = new Gerade(new Koord(0, 0), p4);
g.verschiebeUm(p2.getOrt());
return g;
}
public String toString() {
String s = "Winkel (p1: " + getP1()
+", p2: " + getP2()
+", p3: " + getP3()
+")";
return s;
}
public boolean equals(Object o) {
if (this.getClass().equals(o.getClass())) {
Winkel w = (Winkel) o;
return getP1().equals(w.getP1())
&& getP2().equals(w.getP2())
&& getP3().equals(w.getP3());
}
return false;
}
public Object clone() {
return new Winkel(getP1(), getP2(), getP3());
}
}
Inkreis.java:
class Inkreis {
public static void main(String args[]) {
// Dreieck
Dreieck d1 = new Dreieck(new Koord(-2, -4),
new Koord(4, -2),
new Koord(-2, 4));
System.out.println("d1:" + d1);
System.out.println("");
// Kreis durch Dreieckpunkte mittels 2 Strecken und
// deren Mittelsenkrecheten
System.out.println("Berechne Kreis, der innerhalb des" +
" Dreiecks liegt und dessen Seiten berührt" +
" (Inkreis).\n");
//
Winkel erzeugen und Winkelhalbierende berechnen
4
Winkel w1 = new Winkel(new
new
new
Winkel w2 = new Winkel(new
new
new
Punkt(d1.getQ()),
Punkt(d1.getOrt()),
Punkt(d1.getP()));
Punkt(d1.getOrt()),
Punkt(d1.getP()),
Punkt(d1.getQ()));
System.out.println("Winkel 1:\n" + w1);
System.out.println("Winkel 2:\n" + w2);
System.out.println("");
// Winkelhalbierende
Gerade w1_halb = w1.winkelhalbierende();
Gerade w2_halb = w2.winkelhalbierende();
System.out.println("Winkelhalbierende von w1: " + w1_halb);
System.out.println("Winkelhalbierende von w2: " + w2_halb);
System.out.println("");
// Schnittpunkt
Koord k = w1_halb.schnittMit(w2_halb);
System.out.println("Schnittpunkt der Winkelhalbierenden:" + k);
System.out.println("");
// Orthogonale zu einer Seite des Dreiecks, verschieben nach k,
// Gerade erzeugen und schneiden mit der genutzten Seite.
Koord orthogonale = d1.getP().minus(d1.getOrt()).orthogonal();
Gerade senkrecht = new Gerade(k, k.plus(orthogonale));
Koord k2 = new Gerade(d1.getOrt(),d1.getP()).schnittMit(senkrecht);
double d = k.minus(k2).betrag();
System.out.println("Radius = Abstand von Punkt1 zu Schnittpunkt:" + d);
System.out.println("");
// Kreis
System.out.println("Ergebnis ist der Umkreis des Dreiecks:");
Kreis kr2 = new Kreis(k, d);
System.out.println(kr2 + "\n");
}
}
5
Herunterladen