Kapitel 4 - Ablaufsteuerung 4.1 4.2 4.3 4.4 4.5 Algorithmik 1 Ausdrücke Ablaufsteuerung Methoden Methoden in Klassen Methoden ausgewählter Bibliotheksklassen Prof. Dr. Michael Philippsen / Prof. Dr. Herbert Stoyan Handy aus! Friedrich-Alexander-Universität Erlangen-Nürnberg Informatik 2/8 Programmiersysteme / Künstliche Intelligenz Friedrich-Alexander-Universität Erlangen-Nürnberg Algorithmik 1, WS 2004/05, Folie 4-2 1.6 Imperative Programmiersprache 4.1 Ausdrücke Wenn der Mensch zu einem Problem einen Algorithmus sucht und formuliert, so denkt er am liebsten in Problemstrukturen und der Begrifflichkeit der Problemdomäne. Die Maschinenbefehle des von-Neumann-Rechners sind nur auf die Rechner-Architektur ausgerichtet (und haben gar nichts mit dem zu lösenden Problem zu tun.) Grundoperationen für primitive Typen Eine zustandsorientierte bzw. imperative Programmiersprache ist das gesuchte Bindeglied: y Am Problem orientierte Datenstrukturen und Begrifflichkeiten lassen sich ausdrücken (Zustand). y Die Verfahrensanweisungen haben befehlenden/imperativen Charakter und schreiben genau vor, welche Arbeitsschritte (problemorientiert) in welcher Reihenfolge erledigt werden muss. Hochsprache, da abstrakte Anweisungen und Datenstrukturen Der Übersetzer („compiler“) y bildet Datenstrukturen auf Speicherzellen ab. y bildet Verfahrensanweisungen auf Maschinenbefehle ab. Friedrich-Alexander-Universität Erlangen-Nürnberg Algorithmik 1, WS 2004/05, Wiederholungsfolie Basistyp M. Philippsen Grundoperationen (Auswahl) boolean ==, !=, !(not), &(and), |(inkl. or), ^(exkl. or), &&(and), ||(inkl. or) Test auf gleich/ungleich Strikte Auswertung s.u. Faule Auswertung byte, short, int, long ==, !=, <, >, <=, >=, +, -, ++ (unär), -- (unär), *, /, % (mod), ~(compl.), &(and), |(inkl.or), ^(exkl.or), << (left shift), >> (right shift sign), >>> (right shift no-sign) Vergleiche, liefern boolean „Strichrechnung“ „Punktrechnung“ Operationen auf der Binärdarstellung float, double ==, !=, <, >, <=, >=, +, -, ++ (unär), -- (unär), *, /, % (mod) Vergleiche, liefern boolean „Strichrechnung“ „Punktrechnung“ char + Konkatenation Friedrich-Alexander-Universität Erlangen-Nürnberg M. Philippsen Algorithmik 1, WS 2004/05, Folie 4-4 M. Philippsen 4.1 Ausdrücke 3.1 Variablen einfachen Typs Unäre/binäre „Strichrechung“ am Beispiel Pre- und Postinkrement am Beispiel a + b Addition von a und b zwei Operanden Æ binärer Operator a++ ++a Inkrementiere a um 1 (nach der Auswertung von a) Inkrementiere a um 1 (vor der Auswertung von a) ein Operand Æ unärer Operator Ausdruck b = (a = a + 1); M. Philippsen 4.1 Ausdrücke (15 =) 00001111 (15 =) 00001111 (-1 =) 11111111 wird zu 01111000 (= 120) wird zu 00000001 (= 1) wird zu 00011111 (= 31) Speicherung negativer Zahlen im 2er Komplement: Invertiere jede Bitposition und addiere dann 1 (-1 =) 11111111 >>> ignoriert Vorzeichen: von links neue Nullen einfügen wird zu 11111111 ( = -1) Vorzeichen-Bit 14 | 13: 3 (14 =) 00001110 (13 =) 00001101 „und“ 00001100 (= 12) >> beachtet Vorzeichen: von links altes Vorzeichen-Bit einf. (14 =) 00001110 (13 =) 00001101 „oder“ 00001111 (= 15) M. Philippsen Grundoperatoren kombiniert mit Zuweisung = += -= *= /= %= |= &= ^= <<= >>= >>>= Friedrich-Alexander-Universität Erlangen-Nürnberg Algorithmik 1, WS 2004/05, Folie 4-7 Algorithmik 1, WS 2004/05, Folie 4-6 4.1 Ausdrücke Operationen auf der Binärdarstellung am Beispiel 14 & 13: 3 Friedrich-Alexander-Universität Erlangen-Nürnberg Algorithmik 1, WS 2004/05, Folie 4-5 -1 >> 3: 2 b = ++a; Änderung des Vorzeichens von a ein Operand Æ unärer Operator Friedrich-Alexander-Universität Erlangen-Nürnberg 15 << 3: 15 >> 3: -1 >>> 3: Wert von b, nachher 2 b = a++; y Beispiele (arr habe Typ int[]) arr[a++] greift auf arr[a] zu und erhöht a anschließend arr[++a] greift auf arr[a+1] zu, anschließend ist a erhöht arr[a]++ inkrementiert arr[a] ++arr[a] inkrementiert arr[a] -a Wert von a, Wert von a, vorher nachher Zuweisung Inkrementierung, z. B. alter += 80 (entspricht alter = alter + 80) Dekrementierung, z. B. alter -= 80 (entspricht alter = alter - 80) Skalierung, z. B. alter *= 2 (entspricht alter = alter * 2) Division, z. B. alter /=2 (entspricht alter = alter / 2) Restebildung, z. B. alter %= 10 (entspricht alter = alter % 10) bitweises Oder bitweises Und bitweises Exklusives Oder (Entweder-Oder) Verschieben nach links, z. B. alter <<= 2 (entspricht alter = alter << 2) Verschieben nach rechts (mit Vorzeichenerhalt), z. B. alter >>= 2 (entspricht alter = alter >> 2) Verschieben nach rechts (ohne Vorzeichenerhalt) z. B. alter >>>= 2 (entspricht alter = alter >>> 2) Friedrich-Alexander-Universität Erlangen-Nürnberg M. Philippsen Algorithmik 1, WS 2004/05, Folie 4-8 M. Philippsen 4.1 Ausdrücke 4.1 Ausdrücke Jede Variable, jede Konstante und jedes Literal besitzt einen Typ: Beispiele für Typfehler y Festlegung des gültigen Wertebereichs y Festlegung der anwendbaren Operationen 5 + true Typsicherheit: Auf Operanden können nur die ihrem Typ entsprechenden Operationen angewandt werden. Name der Quellcode-Datei und Zeilennummer des Fehlers Übersetzerlauf: In typsicheren Programmiersprachen kann der Übersetzer für jeden Operanden zu jeder Zeit den zugehörigen Typ ermitteln und damit feststellen, ob eine Operation anwendbar ist. y wenn nicht liefert der Übersetzer eine Fehlermeldung. y somit lassen sich mit Typen manche Fehler ermitteln, bevor ein Schaden angerichtet wird: Verbesserte Korrektheit von Programmen (statische Typsicherheit). Friedrich-Alexander-Universität Erlangen-Nürnberg Algorithmik 1, WS 2004/05, Folie 4-9 binärer +-Operator ist nur für numerische Typen erklärt. Der Übersetzer stellt fest, dass true ein Wahrheitswert und damit kein numerischer Wert ist Æ Fehlermeldung > javac Test.java ... Test.java:4: operator + cannot be applied to int,boolean a = 5 + true; ^ ... Stelle des Fehlers Quellcode-Zeile Friedrich-Alexander-Universität Erlangen-Nürnberg M. Philippsen Algorithmik 1, WS 2004/05, Folie 4-10 M. Philippsen 4.1 Ausdrücke 4.1 Ausdrücke (Statischer) Typ eines Ausdrucks (Statischer) Typ einer Zuweisung Der Typ eines Ausdrucks kann zur Übersetzungszeit bestimmt werden und leitet sich im wesentlichen aus den Typen der Teilausdrücke und des angewendeten Operators ab. Die Typen der linken und der rechten Seite einer Zuweisung müssen zusammenpassen. Nicht nur Ausdrücke haben einen Typ, sondern auch Zuweisungen. Zuweisungen liefern als Wert das jeweilige Ergebnis der rechten Seite. Beispiel: Beispiel: int a = 0; float b = 2; boolean c; c = a == b; // // // c = a * b; // // // c = c * c; // int i, j; i = j = 0; Typ des Ausdrucks a == b ist boolean, a wird implizit in float gewandelt (s.u.), alles ok. Typ des Ausdrucks a * b ist float, a wird implizit in float gewandet (s.u.), Fehler bei der Zuweisung! Fehler, da * nicht auf boolean anwendbar. Friedrich-Alexander-Universität Erlangen-Nürnberg Algorithmik 1, WS 2004/05, Folie 4-11 // i und j wird der // Wert 0 zugewiesen, // da j = 0 den Wert 0 liefert Friedrich-Alexander-Universität Erlangen-Nürnberg M. Philippsen Algorithmik 1, WS 2004/05, Folie 4-12 M. Philippsen 4.1 Ausdrücke 4.1 Ausdrücke Faule versus strikte Auswertung Beispiel: Wert des gesammelten Kleingelds Die Operatoren && und || heißen auch bedingte logische Operatoren, da sie ihren rechten Operanden nur dann auswerten, wenn dies wirklich nötig ist. Sie sind in diesem Sinne „faul“. y In ((b=false) && (c=true)) wird also die Zuweisung zu c nicht ausgeführt, da der Wert der Zuweisung zu b false ist. Da der linke Operand von && schon falsch ist, kann der Gesamtausdruck nicht mehr wahr werden, die Auswertung des rechten Operanden wird eingespart. Im Gegensatz dazu evaluieren die symmetrischen logischen Operatoren &, | und ^ stets (strikt) beide Operanden. Beispiel: y Durch faule Auswertung führt folgender Ausdruck nicht zur Division durch Null: (x != 0) && ((1-x)/x > 1) y Durch strikte Auswertung gibt es hier bei x=0 einen Fehler: (x != 0) & ((1-x)/x > 1) Friedrich-Alexander-Universität Erlangen-Nürnberg M. Philippsen 4.1 Ausdrücke = = = = = = = 10; 2; 0; 4; 1; 3; 1; Variablenvereinbarungen Variablendeklarationen Meist mit Initialisierung Namenskonvention: • Erster Buchstabe klein • Großbuchstabe bei neuem Wort zusammengesetzter Bezeichner gesamt = cents + 2 * zweiCentStücke + 5 * fünfer + 10 * zehner + 50 * fünfziger + 100 * euro + 200 * zweiEuro; Zuweisung, Ausdruck mit Punkt-vor-Strichrechnung, statischer Typ ebenfalls int. Algorithmik 1, WS 2004/05, Folie 4-14 M. Philippsen 4.1 Ausdrücke Auswertungsreihenfolge für Ausdrücke Gemäß Präzedenz/Vorrangregeln, innerhalb dieser: links vor rechts. Präzedenz in Java: (mit expliziter Klammerung zu umgehen) Postfix-Operatoren unäre Operatoren Erzeugung oder Typumwandlung Multiplikationsoperatoren Additionsoperatoren Verschiebeoperatoren Vergleichsoperatoren Gleichheitsoperatoren Bitoperator Und Bitoperator exklusives Oder Bitoperator inklusives Oder logisches Und logisches Oder Fragezeichenoperator Zuweisungsoperatoren cents zweiCentStücke fünfer zehner fünfziger euro zweiEuro gesamt; Friedrich-Alexander-Universität Erlangen-Nürnberg Algorithmik 1, WS 2004/05, Folie 4-13 y y y y y y y y y y y y y y y int int int int int int int int [] . (params) expr++ expr-++expr --expr +expr -expr ! ~ new (type) expr */% „Punkt-vor-Strich“ +<< >> >>> < > <= >= instanceof (später mehr) == != Faule Auswertung (Operanden & vor Operatoranwendung ^ berechnen) nur für &&, ||, ? | && || ?: = += -= *= /= %= >>= <<= >>>= &= ^= |= Typumwandlung auf primitiven Typen (1) Erforderlich, wenn der geforderte Typ eines Wertes nicht mit dem tatsächlichem Typ übereinstimmt. Bedingte Freizügigkeit wegen Typsicherheit! Implizite Umwandlung bei Zuweisung a = b, wenn Wertebereich nicht verkleinert wird („widening“) Typ von b Typ von a byte short, int, long, float, double short, char int, long, float, double int long, float, double Genauigkeitsverluste möglich! long float, double Genauigkeitsverluste möglich! float double Reihenfolge muss beachtet werden: Zuweisungen haben Seiteneffekte. Friedrich-Alexander-Universität Erlangen-Nürnberg Algorithmik 1, WS 2004/05, Folie 4-15 Friedrich-Alexander-Universität Erlangen-Nürnberg M. Philippsen Algorithmik 1, WS 2004/05, Folie 4-16 M. Philippsen 4.1 Ausdrücke 4.1 Ausdrücke Typumwandlung auf primitiven Typen (2) Typumwandlung auf primitiven Typen (3) Implizite Umwandlung in Ausdrücken, um definierten Operator anzuwenden, wenn Wertebereich nicht verkleinert wird. y Beispiel: int a = 0; float b = 2; boolean c; c = a == b; // a wird implizit in float gewandelt Bei ++, -- auf byte, short, char wird Wert zu int. Explizite Typwandlung („casting“). double pi = 3.14; int i = 8; double k = pi * i; //3.14 implizit geweitet floatÆdouble int k1 = (int) (pi * i); int k2 = ((int) pi) * i; long l = (int) k * 2000; y Voranstellen des Zieltyps, z.B. short s = (short) l; long a = 35; int b = (int) a; wandelt eventuell unter Informationsverlust. y Einschränkungen beachten, jedoch Wandlungen zwischen allen numerischen Typen erlaubt. Friedrich-Alexander-Universität Erlangen-Nürnberg Algorithmik 1, WS 2004/05, Folie 4-17 //i implizit geweitet intÆdouble //k = 25.12 //25.12 explizit auf int verkleinert //Informationsverlust: k1=25 //pi wird auf int verkleinert (3) //Informationsverlust: k2=24 //k wird auf int verkleinert (25) //l = 50000 //Sedezimaldarstellung: 000000000000C350 //Informationsverlust: //Binärdarstellung: 1100 0011 0101 0000 //2er Komplement -1 1100 0011 0100 1111 // invertieren 0011 1100 1011 0000 //s = -15536 Aufgabe: nachrechnen Friedrich-Alexander-Universität Erlangen-Nürnberg M. Philippsen Algorithmik 1, WS 2004/05, Folie 4-18 M. Philippsen 4.2 Ablaufsteuerung 4.2 Ablaufsteuerung Anweisungen Gültigkeitsbereiche Eine Anweisung ist eine Abstraktion von (ein höherwertiges Äquivalent zu) den Operationen des realen Rechners. Anweisung wird daher als eine Ausführungseinheit betrachtet. Da imperatives Programmieren Zustandsübergänge bestimmt: Das Ziel der Ablaufsteuerung ist die Steuerbarkeit von Schreib/LeseZugriffen von Variablen und Attributen anhand von vorausgehenden Zuständen. Eine Anweisung ist entweder Ein Gültigkeitsbereich ist der Bereich, in dem ein lokaler (Variablen-)Name eine und dieselbe Referenz hat und somit einen Wert liefert. y Der Gültigkeitsbereich einer Variablen beginnt nach ihrer Deklaration und endet mit dem Ende des Blocks, in dem sie deklariert wurde. y Bei Wiederverwendung des Namens in einem inneren Block gilt dort der innere Name. (Das ist in Java nicht möglich, wohl aber in anderen Sprachen.) y Der Gültigkeitsbereich einer Variablen kann somit zur Übersetzungszeit bestimmt werden. Beispiel für geschachtelte Blöcke mit Gültigkeitsbereichen: { int a int b { int } c; // y eine einfache Anweisung mit Terminator „;“ Beispiel: int c = a*a + b*b; //Zuweisung y oder ein Block, der eine Anweisungsfolge einschließlich Vereinbarung lokaler Variablen mit { und } klammert = 2 * 2; = 3 * 3; c = a + b; Fehler c gültig hier b gültig hier a gültig hier In Java können hier weder a noch b neu deklariert werden. In der Programmiersprache C geht das. Dann sind die äußeren a,b ab hier ungültig. } Die Gültigkeitsbereiche von Attributen einer Klasse unterscheiden sich wesentlich von denen von Variablen. Dazu mehr in Kapitel 5. Friedrich-Alexander-Universität Erlangen-Nürnberg Algorithmik 1, WS 2004/05, Folie 4-19 Friedrich-Alexander-Universität Erlangen-Nürnberg M. Philippsen Algorithmik 1, WS 2004/05, Folie 4-20 M. Philippsen / H. Stoyan 4.2 Ablaufsteuerung 4.2 Ablaufsteuerung Hintereinanderausführung, Sequenz Bedingte Anweisung, Fallunterscheidung, Alternative (1) Reine Hintereinanderschreibung. Allgemeine Form: if (<boolean-Ausdruck>) y Beispiel: Anweisungsfolge A1; A2; A3; ... Anweisungsfolgen führen einen Anfangszustand z0 in einen Endzustand ze über. y Beispiel: Vertauschungsblock { int h; ij ij h = i; ijh i = j; ijh j = h; } ijh <Anweisung1> else Beispiel: if (i > j) max = i; else max = j; Im Flussdiagramm: ijh ij j Zur besseren Lesbarkeit schreibt man im Programm jede Anweisung in eine neue Zeile. Im Flussdiagramm: A2 „else-Teil“ <Anweisung2> zustandsdefinierende Variablen A1 „then-Teil“ <boolean-Ausdruck> <Anweisung1> n <Anweisung2> A3 oder unter einander Friedrich-Alexander-Universität Erlangen-Nürnberg Algorithmik 1, WS 2004/05, Folie 4-21 M. Philippsen Friedrich-Alexander-Universität Erlangen-Nürnberg Algorithmik 1, WS 2004/05, Folie 4-22 M. Philippsen 4.2 Ablaufsteuerung 4.2 Ablaufsteuerung Bedingte Anweisung, Fallunterscheidung, Alternative (2) Bedingte Anweisung, Fallunterscheidung, Alternative (3) else-Teil kann entfallen ⇒ einseitige bedingte Anweisung Allgemeine Form: Bedingter Ausdruck mit Ergebnis/bedingter Operator/?-Operator: Beachte: diese Form der Ablaufstruktur ist redundant. if (<boolean-Ausdruck>) <Anweisung> Beispiel: if (i > j) { int h; h = i; i = j; j = h; } Beispiel: Statt int max; if (i > j) max = i; else max = j; Im Flussdiagramm: j könnte man auch schreiben: <boolean-Ausdruck> <Anweisung> int max = i > j ? i : j; n if ist kein Operator und hat kein Ergebnis. Friedrich-Alexander-Universität Erlangen-Nürnberg Algorithmik 1, WS 2004/05, Folie 4-23 y Allgemeine Form: <bed> ? <Ausdruck1> : <Ausdruck2> y Wenn <bed> zu true ausgewertet wird, dann ist <Ausdruck1> das Ergebnis des ?-Operators. Sonst ist <Ausdruck2> das Ergebnis. Friedrich-Alexander-Universität Erlangen-Nürnberg M. Philippsen Algorithmik 1, WS 2004/05, Folie 4-24 M. Philippsen / H. Stoyan 4.2 Ablaufsteuerung 4.2 Ablaufsteuerung Die spezielle Form der Kaskade Kaskaden von bedingten Anweisungen sind möglich. Beispiel: // Berechne das Vorzeichen von a. (a weiter oben definiert) int signum; if (a > 0) {signum = 1;} else if (a < 0) {signum = -1;} else {signum = 0;} Beachte: eine geeignete Klammerung und Einrückung macht den Code besser lesbar und vermeidet Programmierfehler. Hier besser: // Berechne das Vorzeichen von a. (a weiter oben definiert) int signum; if (a > 0) { signum = 1; } else if (a < 0) { signum = -1; } else { signum = 0; } if (i == k1) A1; else if (i == k2) A2; else if (i == k3) A3; ... else A0; kann übersichtlicher als switch-Anweisung geschrieben werden // i muss vom Typ byte, short, int oder char sein switch (i) { case k1: A1; break; // ki müssen Literale vom Typ byte, case k2: A2; break; // short, int, char sein, und i muss case k3: A3; break; // vom entsprechenden Typ sein. ... break beendet gesamte default: A0; Beachte: diese Form switch-Anweisung, sonst } Fortsetzung im Folgefall. Friedrich-Alexander-Universität Erlangen-Nürnberg Algorithmik 1, WS 2004/05, Folie 4-25 Friedrich-Alexander-Universität Erlangen-Nürnberg M. Philippsen / H. Stoyan Algorithmik 1, WS 2004/05, Folie 4-26 4.2 Ablaufsteuerung 4.2 Ablaufsteuerung switch-Beispiel mit break while-Schleife (1) numDays = 31; //normal switch (month) { case 4: case 6: case 9: case 11: numDays = 30; break; case 2: //Schaltjahr-Code } Ohne break „rutschen“ diese Fälle durch bis zum Code für den Fall 11. Ohne default-Fall wird bei nicht explizit aufgeführten Monaten gar nichts gemacht. der Ablaufstruktur ist redundant. M. Philippsen Grundgedanke der Steuerung: Wiederholte Ausführung von Aktionen, bis eine Zielbedingung erfüllt ist. Standardform: while (<boolean-Ausdruck>) <Anweisung> <Anweisung> muss das Ergebnis der Bedingung beeinflussen, sonst „Endlosschleife“ – keine Terminierung. Im Flussdiagramm: <boolean-Ausdruck> n j Allgemein: Die break-Anweisung beendet (nicht nur innerhalb der switch–Anweisung) die Ausführung der sie umgebenden Ablaufstruktur. Friedrich-Alexander-Universität Erlangen-Nürnberg Algorithmik 1, WS 2004/05, Folie 4-27 <Anweisung> gehört nicht zum Diagramm Friedrich-Alexander-Universität Erlangen-Nürnberg M. Philippsen Algorithmik 1, WS 2004/05, Folie 4-28 M. Philippsen / H. Stoyan 4.2 Ablaufsteuerung 4.2 Ablaufsteuerung while-Schleife (2) Beispiel für eine while-Schleife (als Block notiert) „Schreibtischlauf“ kgV(a,b,c) dreier ganzer Zahlen Standardform: while (<boolean-Ausdruck>) <Anweisung> Schleifentest Schleifenrumpf while-Schleifen heißen auch abweisende Schleifen, weil ihr Rumpf u.U. nie durchlaufen wird (falls die Bedingung <boolean-Ausdruck> schon vor Betreten des Schleifenrumpfes zu false ausgewertet wird). Jede Anweisung, die den Schleifenrumpf abbricht, beendet die whileSchleife: y Abbruch jedes Blocks und damit auch einer while-Schleife ist möglich mit der break-Anweisung. y Später: à return-Anweisung zum Beenden der umschließenden Methode à Ausnahmebehandlung a 5 // a, b, c weiter oben definiert... 5 int aRes = a, bRes = b, cRes = c; 5 while (aRes != bRes || bRes != cRes){ 5 5 if (aRes < bRes) { 5 aRes = aRes + a; 5 } else if (bRes < cRes) { 5 bRes = bRes + b; 5 } else { 5 cRes = cRes + c; 5 } 5 5 } Friedrich-Alexander-Universität Erlangen-Nürnberg M. Philippsen 4.2 Ablaufsteuerung Algorithmik 1, WS 2004/05, Folie 4-30 terminiert bei: 5 3 2 30 30 30 M. Philippsen 4.2 Ablaufsteuerung do-while-Schleife for-Schleife Redundante Ablaufstruktur Standardform: do <Anweisung> while (<boolean-Ausdruck>); Schleifentest wird am Ende des Schleifenrumpfes evaluiert; daher mindestens ein Durchlauf durch den Rumpf; nicht-abweisende Schleife Im Flussdiagramm: <boolean-Ausdruck> Friedrich-Alexander-Universität Erlangen-Nürnberg Bedeutung: 1. Erst wird der Initialisierungsausdruck ausgewertet (und ggf. werden die dort deklarierten Variablen angelegt) 2. Dann wird der Schleifentest ausgewertet. Wenn falsch: Schleifenende. Also: abweisende Schleife 3. Ausführung der <Anweisung> 4. Ausführung des <Inkrementausdrucks>, der typischerweise die Variablen verändert (hochzählt), die in der Initialisierung gesetzt und im Schleifentest mit Grenzwerten verglichen werden. n j Redundante Ablaufstruktur Standardform: for (<Initialausdruck>; <boolean-Ausdruck>; <Inkrementausdruck>) <Anweisung> <Anweisung> Algorithmik 1, WS 2004/05, Folie 4-31 c aRes bRes cRes 2 5 3 2 2 5 3 4 2 5 6 4 2 10 6 4 2 10 6 6 2 10 6 8 2 10 9 8 2 10 9 10 2 10 12 10 2 15 12 10 2 15 12 12 2 15 12 14 2 15 15 14 … Friedrich-Alexander-Universität Erlangen-Nürnberg Algorithmik 1, WS 2004/05, Folie 4-29 b 3 3 3 3 3 3 3 3 3 3 3 3 3 for-Schleife bei Iteration über einen Wertebereich bequemer als while. Friedrich-Alexander-Universität Erlangen-Nürnberg M. Philippsen Algorithmik 1, WS 2004/05, Folie 4-32 M. Philippsen 4.2 Ablaufsteuerung 4.2 Ablaufsteuerung Beispiel for- versus while-Schleifen Eine for-Schleife kann (im Wesentlichen) nach folgendem Muster auf eine semantisch äquivalente while-Schleife abgebildet werden: for (<Initialausdruck>; <boolean-Ausdruck>; <Inkrementausdruck>) <Anweisung> wird zu: Aufsummieren der Werte einer Reihung int[] a: Initialisierungsausdruck int summe; for (int i = 0; i < a.length; i++) { summe = summe + a[i]; } Bedingung für Betreten und Fortschaltung Wiederholen des Rumpfes Äquivalente Formulierung mit einer while-Schleife: { <Initialausdruck>; while (<boolean-Ausdruck>) { <Anweisung>; <Inkrementausdruck>; } } Aufgabe: Ersetze do-while-Schleife durch while-Schleife. Friedrich-Alexander-Universität Erlangen-Nürnberg M. Philippsen 4.2 Ablaufsteuerung Beispiel: Matrix-Multiplikation × M. Philippsen / H. Stoyan = Assoziationen =2×3+3×4 y vage, unklar, unverständlich, unkonkret y Einzelheiten sind weggelassen y das Farbige, Lebendige wird unterdrückt 13 18 23 18 25 32 23 32 41 Ziel der Abstraktion Programm-Fragment y Über gemeinsame Eigenschaften einer Gruppe von Individuen oder Objekte möglichst einfach sprechen int a[][] = {{2,3}, {3,4}, {4,5}}; int b[][] = {{2,3,4}, {3,4,5}}; int c[][] = new int[3][3]; for (int i=0; i<3; i++) { for (int j=0; j<3; j++) { for (int k=0; k<2; k++) { c[i][j] += a[i][k] * b[k][j]; } } } dazu: y Betonen des prototypischen Charakters bestimmter Individuen oder Objekte 3 geschachtelte for-Schleifen Friedrich-Alexander-Universität Erlangen-Nürnberg Algorithmik 1, WS 2004/05, Folie 4-35 Algorithmik 1, WS 2004/05, Folie 4-34 Abstraktion Geschachtelte Schleifen 2 3 4 3 4 5 Fortschalten am Ende Friedrich-Alexander-Universität Erlangen-Nürnberg Algorithmik 1, WS 2004/05, Folie 4-33 2 3 3 4 4 5 int summe; { Neuer Block int i = 0; (Deklaration und) Initialisierung while (i < a.length) { summe = summe + a[i]; i++; } } oder y Erfinden hypothetischer Gegenstände Friedrich-Alexander-Universität Erlangen-Nürnberg M. Philippsen Algorithmik 1, WS 2004/05, Folie 4-36 H. Stoyan Abstraktion Abstraktion Positive Abstraktion Resultat der Abstraktion y Hervorheben einer gemeinsamen Eigenschaft y alle Dinge/Objekte/Individuen mit der gemeinsamen Eigenschaft stehen in einer Äquivalenzrelation Äquivalenzrelation: reflexiv, symmetrisch, transitiv Äquivalenzklasse = Klasse von Dingen/Objekten/Individuen mit äquivalenten Ausprägungen Konsequenz: Aussage über x aus Äquivalenzklasse => Aussage über beliebiges y aus dieser Klasse Friedrich-Alexander-Universität Erlangen-Nürnberg Algorithmik 1, WS 2004/05, Folie 4-37 y die Aussagen hängen nur noch von den die Äquivalenzrelation definierenden Eigenschaften ab y wir sprechen so, als ob es Dinge/Objekte/Individuen gäbe, die nur diese Eigenschaften haben y das sind fiktive, virtuelle Dinge/Objekte/Individuen Beispiele y Zahl: Klasse der Grundobjekte: Figuren aus Zählzeichen, Äquivalenzrelation: Bestehen aus gleichvielen Teilzeichen y Aussage: Klasse der Grundobjekte: Sätze, Äquivalenzrelation: Inhaltsgleichheit y Funktion: Klasse der Grundobjekte: Terme (Abbildungsvorschriften), Äquivalenzrelation: gleicher Wert beim Einsetzen gleicher Argumentwerte y Fehler: Klasse der Grundobjekte: Beschreibung von Fehlersituationen, Äquivalenzrelation: gleiche Symptomkombination (gleiche Auswirkungen, gleiche Korrekturbehandlung) Friedrich-Alexander-Universität Erlangen-Nürnberg H. Stoyan Algorithmik 1, WS 2004/05, Folie 4-38 H. Stoyan Abstraktion Abstraktion Funktionale Abstraktion Funktionale/prozedurale Abstraktion 1.Art: strukturell ähnliche Codestücke realisieren dieselbe Funktion/Prozedur Deshalb Einführung der Methode (Produkt der Abstraktion): y identische Folgen von Anweisungen bewirken im gleichen Zustand dasselbe y wenn die Anweisungen strukturell gleich sind, aber verschiedene Parameternamen vorkommen, hängt die Wirkung von der Belegung der Parameter ab Beispiel: Math.pow(x,0.5) und Math.pow(wert,0.5) sind struktuerell ähnlich Funktionale/prozedurale Abstraktion 2.Art: verschiedene Codestücke können dieselbe Funktion/Prozedur realisieren! Beschreibung durch: Eingabe- und Ausgabebedingungen Beispiel: float wurzel1(float wert){return Math.pow(wert,0.5)} float wurzel2(float w){return Math.sqrt(w)} realisieren dieselbe Funktion, Eingabebegingung: x>0 Ausgabebedingung: y2=x Funktions/Prozedurname als Symbol für diese gemeinsamen Bedingungen Friedrich-Alexander-Universität Erlangen-Nürnberg Algorithmik 1, WS 2004/05, Folie 4-39 float wurzel(float wert){return Math.pow(wert,0.5)} Friedrich-Alexander-Universität Erlangen-Nürnberg H. Stoyan Algorithmik 1, WS 2004/05, Folie 4-40 H. Stoyan Abstraktion 4.3 Methoden Daten-Abstraktion Mit ähnlichen Daten geht man auf ähnliche Weise um Arbeitsmittel: Methode („method, operation“) y y y y y y In der Objektorientierung senden Objekte Nachrichten, die zur Aktivierung von Methoden führen (siehe UML-Sequenzdiagramm). Konstruktoren Zugriffsfunktionen Veränderungsfunktionen Konvertierungsfunktionen Vergleichsfunktionen usw. In den meisten Programmiersprachen ist aber das Senden und Empfangen der Nachrichten zum Aufruf von Methoden degeneriert. die konkrete Realisierung der Datenobjekte (mit Feld, Liste, Record, o.ä. ist unerheblich (und ändert sich auch oft) Hat man zwei oder mehr Gruppen von gleichen derartigen Funktionen (mit gleichen Eingabe/Ausgabe-Bedingungen kann man demnach von einer Datensorte sprechen: Eine Methode ist ein benannter Anweisungsblock, dessen Inhalt durch eine Ein/Ausgabe-Schnittstelle gekapselt ist und dessen Funktionalität evtl. an mehreren Stellen verwendet werden kann. Der Anweisungsblock heißt auch Methodenrumpf. y abstrakter Datentyp, verwirklicht im Klassenkonzept y Klassenname als Name für diese gemeinsame Gruppe von Bedingungen Friedrich-Alexander-Universität Erlangen-Nürnberg Algorithmik 1, WS 2004/05, Folie 4-41 Friedrich-Alexander-Universität Erlangen-Nürnberg H. Stoyan Algorithmik 1, WS 2004/05, Folie 4-42 4.3 Methoden 4.3 Methoden Signatur und Rumpf Methodeklaration Nach außen wird eine Methode durch ihre Signatur bestehend aus Ergebnistyp, Name sowie Anzahl und Typen der Parameter beschrieben: Vereinbarung: <Ergebnistyp> <Name> ( <Parameterliste> ) Signatur y Eine Methode hat ein Ergebnis von einem festen Typ (der Ausgabe-Teil der Schnittstelle). y DieTypen der Parameter der Methode repräsentieren den Eingabe-Teil der Schnittstelle. Es handelt sich dabei um eine feste Liste von n getypten Variablen. Sie gelten im Methodenrumpf als lokale Variablen. Die Deklaration von zwei Methoden mit derselben Signatur in einer Klasse ist nicht erlaubt. M. Philippsen Signatur oder Methodenkopf <Ergebnistyp> <Methodenname> (<Parametertyp 1> <Param.name 1>,... , <Parametertyp n> <Param.name n>) { Methodenrumpf // Anweisungen hier. } Methoden ohne Ergebnis sind auch möglich: Vereinbarungen wie zuvor, aber mit void als <Ergebnistyp>. In Java werden Methoden immer in Klassen definiert! y In Java gehört der Ergebnistyp nicht zur Signatur. Friedrich-Alexander-Universität Erlangen-Nürnberg Algorithmik 1, WS 2004/05, Folie 4-43 Friedrich-Alexander-Universität Erlangen-Nürnberg M. Philippsen Algorithmik 1, WS 2004/05, Folie 4-44 M. Philippsen 1.6 Imperative Programmiersprache 4.3 Methoden Euklids Algorithmus in Java Aufrufen von Methoden Ein Methodenaufruf hat die Form <Methodenname>(<Argument 1>, … ,<Argument n>) ... int ggt(int a, int b) { if (a==b) return a; else if (a<b) return ggt(a,b-a); else return ggt(a-b,b); } ... (Das zum Verständnis dieses Programms erforderliche Detailwissen folgt später …) nah genug am Algorithmus, damit der Mensch problembezogen denken kann. nah genug am Konzept der Zustandstransformationen (Speichermodifikationen) durch Maschinenbefehle Friedrich-Alexander-Universität Erlangen-Nürnberg Algorithmik 1, WS 2004/05, Wiederholungsfolie Bei der Abarbeitung des Methodenaufrufs werden die Anweisungen im Methodenrumpf (der Methode mit dem angegebene Namen) ausgeführt. <Argument 1> bis <Argument n> sind dabei Ausdrücke, die zuvor berechnet werden und deren Werte den Parametern 1 bis n der Methode zugewiesen werden. Da die Parameter typisiert sind, müssen die jeweiligen Ausdruckstypen zu den Parametertypen passen (gleicher Typ oder implizit konvertierbar). Im Methodenrumpf sind nur die dort deklarierten Variablen und die Parameter sichtbar. Friedrich-Alexander-Universität Erlangen-Nürnberg M. Philippsen Algorithmik 1, WS 2004/05, Folie 4-46 M. Philippsen 4.3 Methoden 4.3 Methoden Zurückgeben von Ergebnissen Methodendeklaration und -aufruf Bei Methoden mit echtem Ergebnistyp (ungleich void) ist der Methodenaufruf ein Ausdruck, dessen Typ identisch ist mit dem Ergebnistyp der Methode Der Rückgabewert der Methode wird im Methodenrumpf mit return <Wert>; zurückgegeben, wodurch die Methodenausführung beendet wird. Der Typ des Werts muss natürlich zum Ergebnistyp der Methode passen. Bei void-Methoden ohne echten Ergebnistyp, wird die Methode mit return; beendet. 11 und 47 sind Argumente, die in die Parameter std und min übergeben werden. Uhr c = new Uhr(); c.setzeZeit(11, 40+7); // setzt die Uhrzeit auf 11:47 Uhr long l = c.leseZeitInSekunden(); // l ist 42420 Friedrich-Alexander-Universität Erlangen-Nürnberg Algorithmik 1, WS 2004/05, Folie 4-47 Die Parameter std und class Uhr { min sind lokale Variablen ... im Inneren der Methode void setzeZeit(long std, long min) { stunden = std; minuten = min; } Kein Ergebnistyp (void), long leseZeitInSekunden() { daher keine return-Anw. return (stunden*3600)+(minuten*60); } ... Parameterlose Methode } Friedrich-Alexander-Universität Erlangen-Nürnberg M. Philippsen Algorithmik 1, WS 2004/05, Folie 4-48 M. Philippsen / H. Stoyan 4.3 Methoden 4.3 Methoden Konzeptionell: Verdeckte Zuweisungen Euklids Algorithmus in Java <Ergebnistyp> <Methodenname> (<Parametertyp 1> <Parametername 1>,..., <Parametertyp n> <Parametername n>) { Parametername 1 = Argument 1; ... Argumentwerte werden Parametername n = Argument n; in lokale Variablen der Methode kopiert. // Anweisungen hier. *erg*= Wert; } Mit der Return-Anweisung wird Resultat in konzeptionelle Ergebnisvariable kopiert. Friedrich-Alexander-Universität Erlangen-Nürnberg Algorithmik 1, WS 2004/05, Folie 4-49 4.3 Methoden Euklids Algorithmus in Java ... ggt(18,12); ... M. Philippsen ... int ggt(int a, int b) { if (a==b) return a; else if (a<b) return ggt(a,b-a); else return ggt(a-b,b); } ... anlegen Methodenschachtel a: 18 b: 12 *erg*: Rücksprungziel konzeptionell: ... else { *erg*=ggt(6,12); return *erg*; } ... Methodenschachtel a: 6 b: 12 *erg*: 6 Rücksprungziel konzeptionell: ... ... if (a<b) { 6 *erg*=ggt(6,6); Æ Bei der Rückkehr aus der aufgerufenen Methode werden die Methodenschachteln wieder abgebaut. XXXXX return *erg*; } ... Friedrich-Alexander-Universität Erlangen-Nürnberg Algorithmik 1, WS 2004/05, Folie 4-51 ... ggt(18,12); ... anlegen Methodenschachtel a: 18 b: 12 *erg*: Rücksprungziel konzeptionell: ... else { *erg*=ggt(6,12); return *erg*; } ... Argumente werden in die Parametervariablen kopiert. ... int ggt(int a, int b) { if (a==b) return a; else if (a<b) return ggt(a,b-a); else return ggt(a-b,b); } ... Æ Zur Laufzeit existieren viele Kopien der methodenlokalen Variablen Methodenschachtel a: 6 Methodenschachtel b: 12 *erg*: Rücksprungziel konzeptionell: ... ... if (a<b) { *erg*=ggt(6,6); return *erg*; } ... a: 6 b: 6 *erg*: 6 Rücksprungziel konzeptionell: ... if (a==b) { *erg*=6; return *erg*; } ... Friedrich-Alexander-Universität Erlangen-Nürnberg Algorithmik 1, WS 2004/05, Folie 4-50 4.3 Methoden Euklids Algorithmus in Java ... ggt(18,12); ... anlegen M. Philippsen / H. Stoyan ... int ggt(int a, int b) { if (a==b) return a; else if (a<b) return ggt(a,b-a); else return ggt(a-b,b); } ... Methodenschachtel a: 18 b: 12 erg: 6 Rücksprungziel konzeptionell: ... else { 6 *erg*=ggt(6,12); XXXXX return *erg*; } ... Friedrich-Alexander-Universität Erlangen-Nürnberg M. Philippsen / H. Stoyan Algorithmik 1, WS 2004/05, Folie 4-52 M. Philippsen / H. Stoyan 4.3 Methoden Euklids Algorithmus in Java ... 6 ggt(18,12); XXXXXXX ... ... int ggt(int a, int b) { if (a==b) return a; else if (a<b) return ggt(a,b-a); else return ggt(a-b,b); } ... 4.3 Methoden Übergabe von Eingabeparametern Wertaufruf („call-by-value“) y Wert des Parameters wird in die lokale Variable kopiert (Wertsemantik) y Wenn der Wert des Parameters im Inneren der Methode verändert wird, dann ändert sich auf Seiten des Aufrufers (am Argument) nichts. y Der Wertaufruf wird in Java bei primitiven Typen benutzt Referenzaufruf („call-by-reference“) y Parameter enthält Referenz auf ein Objekt (Referenzsemantik) y Sowohl das Argument als auch der Parameter verweist auf dasselbe Objekt. y Änderungen am Zustand des Objekts sind daher auch außerhalb der Methode sichtbar. y Der Referenzaufruf wird in Java bei Objekten benutzt. Friedrich-Alexander-Universität Erlangen-Nürnberg Algorithmik 1, WS 2004/05, Folie 4-53 Friedrich-Alexander-Universität Erlangen-Nürnberg M. Philippsen Algorithmik 1, WS 2004/05, Folie 4-54 M. Philippsen 4.3 Methoden 4.3 Methoden Wertaufruf („call-by-value“) Referenzaufruf („call-by-reference“) void demo(int a) { a = 5; //Wertübergabe //geändert wird nur Variable in der //Methodenschachtel return; } ... int a = 4; demo(a); void demo(Uhr u) { u = new Uhr(); //Referenzübergabe //geändert wird nur Variable u in der //Methodenschachtel return; } ... Uhr u = new Uhr(); demo(u); //a hat immer noch den Wert 4; //u zeigt immer noch auf selbes Objekt void demo(Uhr u) { u.stunden = 7; return; } ... Uhr u = new Uhr(); demo(u); //Referenzübergabe //ändert Attribut des übergebenen Ojekts //u.stunden hat neuen Wert Friedrich-Alexander-Universität Erlangen-Nürnberg Algorithmik 1, WS 2004/05, Folie 4-55 Friedrich-Alexander-Universität Erlangen-Nürnberg M. Philippsen Algorithmik 1, WS 2004/05, Folie 4-56 M. Philippsen 4.4 Methoden in Klassen Zusammenfassung der Begriffe Beispiel: Klasse rationaler Zahlen Oberbegriff von 4.3 Methoden Methode / Operation •= Benannte Anweisungsfolge •Deklaration = Kopf + Rumpf •Kopf = Schnittstelle zur Umwelt •Rumpf = lokale Attribute und Anweisungen •Eingabeparameter •Rekursiv aufrufbar Prozedur class Rational { int zähler, nenner; Rational(int z, int n) { zähler = z; nenner = n; } Rational rationalAdd(Rational r) { return new Rational(zähler*r.nenner + nenner*r.zähler, nenner*r.nenner).kürzen(); } ... Funktion •Java: Kein Ergebnisparameter •Aufruf als eigenständige Anweisung kein return •Immer genau ein Ergebnisparameter •Aufruf innerhalb eines Ausdrucks Konstruktor Aufruf im Ausdruck, Referenz als Resultat •Aufruf mit new •Initialisiert ein Objekt } Friedrich-Alexander-Universität Erlangen-Nürnberg Algorithmik 1, WS 2004/05, Folie 4-57 Alle Methoden enthalten einen ersten, impliziten Parameter this mit der vereinbarten Klasse als Typ. Bei Versenden einer Nachricht an ein Objekt dieser Klasse wird this dann durch dieses Empfängerobjekt aktualisiert. Folge: Mit der Nachricht begibt man sich in den Zustandsraum des Empfängerobjektes, um die zugehörige Methode auszuführen. Friedrich-Alexander-Universität Erlangen-Nürnberg M. Philippsen Algorithmik 1, WS 2004/05, Folie 4-58 4.4 Methoden in Klassen 4.4 Methoden in Klassen Beispiel: Klasse rationaler Zahlen Statische Methoden („class method“) Zu interpretieren als this.zähler, this.nenner. Die Attribute des Empfängerobjektes befinden sich in dessen lokalem class Rational { Gültigkeitsbereich, auf sie kann daher int zähler, nenner; unmittelbar zugegriffen werden. Rational(int z, int n) { this kann man explizit verwenden, zähler = z; wenn das Objekt seine eigene nenner = n; Referenz benötigt. } Rational rationalAdd(Rational r) { return new Rational(zähler*r.nenner + nenner*r.zähler, nenner*r.nenner).kürzen(); } ... Nachricht an das durch r referenzierte Objekt, um } dessen Werte nenner und zähler zu beschaffen. Dazu wird dessen Zustandsraum betreten. Friedrich-Alexander-Universität Erlangen-Nürnberg Algorithmik 1, WS 2004/05, Folie 4-59 M. Philippsen Statische Methoden sind einer Klasse und nicht einem Objekt zugeordnet. Sie können nicht auf den Instanzvariablen, sondern nur auf Klassenvariablen operieren. Sie werden mit static gekennzeichnet. Die statische Methode main kennzeichnet den Programmstart. class Uhr { ... public static void main (String[] args) { // Programmstart Uhr c = new Uhr(); c.setzeZeit(10, 00); } // Programmende } Friedrich-Alexander-Universität Erlangen-Nürnberg M. Philippsen Algorithmik 1, WS 2004/05, Folie 4-60 M. Philippsen 4.4 Methoden in Klassen Die main-Methode 4.4 Methoden in Klassen später mehr zu public main-Methode am Beispiel public static void main(String[] argv) {...} ist obligatorisch für jede Java-Applikation. Mit der Ausführung der Main-Methode beginnt die Ausführung des Programms. Die Applikation kann in der Reihung argv eventuell beim Aufruf angegebene Kommandozeilenargumente finden. (Klasse String wird im nächsten Abschnitt näher behandelt.) Datei Demo.java: class Demo { public static void main(String[] argv) { ggt(18,12); } static int ggt(int a, int b) { if (a==b) return a; else if (a<b) return ggt(a,b-a); else return ggt(a-b,b); } } Übersetzen und ausführen: javac Demo.java java Demo Friedrich-Alexander-Universität Erlangen-Nürnberg Friedrich-Alexander-Universität Erlangen-Nürnberg Algorithmik 1, WS 2004/05, Folie 4-61 M. Philippsen Algorithmik 1, WS 2004/05, Folie 4-62 4.4 Methoden in Klassen 4.4 Methoden in Klassen Mehrfachdefinition von Methoden - Überladen („method overloading“) Mehrfachdefinition von Methoden Beispiel: Eine Methode kann innerhalb einer Klasse in mehreren Varianten definiert werden, wenn die Signaturen unterschiedlich sind, aber die Methodennamen gleich. Beim Methodenaufruf wird mittels der Parametertypen die richtige Methodenvariante ausgewählt. y Ähnlich liegen die Verhältnisse, wenn in einer Oberklasse eine Methode definiert ist und in einer Unterklasse die Methode mit einer anderen Signatur neu definiert wird. y Man spricht vom Methoden-Überladen, weil nach Auswahl der Methode die Parameter zur richtigen Methode führen und diese die vorausgewählte Methode ersetzt. Ein Konstruktor kann ebenfalls überladen werden. Friedrich-Alexander-Universität Erlangen-Nürnberg Algorithmik 1, WS 2004/05, Folie 4-63 Ein-/Ausgabe fehlt noch; folgt in Kapitel 5. M. Philippsen class Uhr { ... void setzeZeit(long std, long min) { stunden = std; minuten = min; } void setzeZeit(long std) { setzeZeit(std, 0); // Aufruf der Methode mit } // zwei Parametern ... } Friedrich-Alexander-Universität Erlangen-Nürnberg M. Philippsen / H. Stoyan Algorithmik 1, WS 2004/05, Folie 4-64 M. Philippsen / H. Stoyan 4.5 Methoden ausgewählter Bibliotheksklassen 4.5 Methoden ausgewählter Bibliotheksklassen Java verfügt über eine sehr umfangreiche Bibliothek, in der viele Klassen und Methoden zur Verwendung bereitstehen. Siehe: http://java.sun.com/j2se/1.4.2/docs/api/ Die (zunächst) wichtigsten vordefinierten Klassen befinden sich im Paket java.lang (zu Paketen später mehr). Friedrich-Alexander-Universität Erlangen-Nürnberg Algorithmik 1, WS 2004/05, Folie 4-65 Friedrich-Alexander-Universität Erlangen-Nürnberg M. Philippsen Algorithmik 1, WS 2004/05, Folie 4-66 M. Philippsen 4.5 Methoden ausgewählter Bibliotheksklassen 4.5 Methoden ausgewählter Bibliotheksklassen Konstruktoren der Klasse String (Auszug) String() Initializes a newly created String object so that it represents an empty character sequence. String(char[] value) Allocates a new String so that it represents the sequence of characters currently contained in the character array argument. String(char[] value, int offset, int count) Allocates a new String that contains characters from a subarray of the character array argument. String(byte[] bytes) Constructs a new String by decoding the specified array of bytes using the platform's default charset. String(byte[] bytes, String charsetName) Constructs a new String by decoding the specified array of bytes using the specified charset. Methoden der Klasse String (Auszug) char charAt(int index) Returns the character at the specified index. int compareTo(String anotherString) Compares two strings lexicographically (returns 0 iff equal). int compareToIgnoreCase(String str) Compares two strings lexicographically, ignoring case differences. boolean endsWith(String suffix) Tests if this string ends with the specified suffix. boolean equalsIgnoreCase(String anotherString) Compares this String to another String, ignoring case considerations. int indexOf(int ch) Returns the index within this string of the first occurrence of the specified character. int lastIndexOf(String str) Returns the index within this string of the rightmost occurrence of the specified substring. String replace(char oldChar, char newChar) Returns a new string resulting from replacing all occurrences of oldChar in this string with newChar. String substring(int beginIndex, int endIndex) Returns a new string that is a substring of this string. String toUpperCase() Converts all of the characters in this String to upper case using the rules of the default locale. … String(byte[] bytes, int offset, int length) ... String(byte[] bytes, int offset, int length, String charsetName) ... String(String original) Initializes a newly created String object so that it represents the same sequence of characters as the argument; in other words, the newly created string is a copy of the argument string. ... Friedrich-Alexander-Universität Erlangen-Nürnberg Algorithmik 1, WS 2004/05, Folie 4-67 Friedrich-Alexander-Universität Erlangen-Nürnberg M. Philippsen Algorithmik 1, WS 2004/05, Folie 4-68 M. Philippsen 4.5 Methoden ausgewählter Bibliotheksklassen 4.5 Methoden ausgewählter Bibliotheksklassen Die Klasse java.lang.Math enthält Methoden, die mathematische Funktionen zur Verfügung stellen. Die Methoden dieser Klasse sind statische Methoden. Sie können daher verwendet werden, indem dem Methodennamen „Math.“ vorangestellt wird. Beispiel: Löse a·x² + b·x + c = 0 (mit der Annahme: b² - 4·a·c ≥ 0) Beispiel: Löse a·x² + b·x + c = 0 (mit der Annahme: b² - 4·a·c ≥ 0) double x1, x2, a, b, c; a = 1.0; b = 5.0; c = 6.0; double x1, x2, a, b, c; a = 1.0; b = 5.0; c = 6.0; x1 = (-b + Math.sqrt(b * b - 4 * a * c)) / (2 * a); x2 = (-b - Math.sqrt(b * b - 4 * a * c)) / (2 * a); Zwei unleserliche Zeilen mit fast dem selben Inhalt. Besser und schneller ist: Gemeinsame Teilausdrücke herausziehen und nur einmal in Hilfsvariable auswerten double x1, x2, a, b, c; a = 1.0; b = 5.0; c = 6.0; x1 = (-b + Math.sqrt(b * b - 4 * a * c)) / (2 * a); x2 = (-b - Math.sqrt(b * b - 4 * a * c)) / (2 * a); double wurzel = Math.sqrt(b * b - 4 * a * c); double nenner = 2 * a; x1 = (-b + wurzel) / nenner; x2 = (-b - wurzel) / nenner; Friedrich-Alexander-Universität Erlangen-Nürnberg Algorithmik 1, WS 2004/05, Folie 4-69 Friedrich-Alexander-Universität Erlangen-Nürnberg M. Philippsen 4.5 Methoden ausgewählte Bibliotheksklassen Algorithmik 1, WS 2004/05, Folie 4-70 4.5 Methoden ausgewählter Bibliotheksklassen Konstanten und Methoden der Klasse Math (Auszug) static double E The double value that is closer than any other to e, the base of the natural logarithms. static double PI The double value that is closer than any other to pi, the ratio of the circumference of a circle to its diameter. Returns the absolute value of a double value. float abs(float a) Returns the absolute value of a float value. int abs(int a) Returns the absolute value of an int value. long abs(long a) Returns the absolute value of a long value. double sin(double a) Returns the trigonometric sine of an angle. double exp(double a) Returns Euler's number e raised to the power of a double value. double log(double a) Returns the natural logarithm (base e) of a double value. double max(double a, double b) Returns the greater of two double values. double pow(double a, double b) Returns the value of the first argument raised to the power of the second argument. Die Klasse java.lang.System stellt die Schnittstelle einer laufenden Java-Applikation zur Systemumgebung bereit. Zunächst am wichtigsten sind die Standard-Ein/Ausgabe, über die Zeichen mit der Shell ausgetauscht werden können: static double abs(double a) y static PrintStream out static static static static static y static PrintStream err static static static … Friedrich-Alexander-Universität Erlangen-Nürnberg Algorithmik 1, WS 2004/05, Folie 4-71 M. Philippsen y static InputStream in The "standard" output stream. The "standard" error output stream. The "standard" input stream. Die wichtigsten Methoden von java.lang.PrintStream sind: y void print(String s) y void println() y void println(String x) Print a string. Terminate the current line by writing the line separator string. Print a String and then terminate the line. Friedrich-Alexander-Universität Erlangen-Nürnberg M. Philippsen Algorithmik 1, WS 2004/05, Folie 4-72 M. Philippsen 4.5 Methoden ausgewählter Bibliotheksklassen Beispiel für Ausgabe auf dem Schirm: später mehr zu public class Hello { static public void main(String[] argv) { System.out.println(“Hello World”); } } Die diversen print-Methoden akzeptieren auch primitive Typen, deren Werte dann zur Ausgabe in eine textuelle Repräsentation gebracht werden. Wird den print-Methoden ein Objekt beliebigen Typs übergeben, dann wird die (von Object geerbte oder in der zugehörigen Klasse überschriebene) toString()-Methode aufgerufen, um eine angemessene textuelle Repräsentation des Objekts zu erzeugen. Friedrich-Alexander-Universität Erlangen-Nürnberg Algorithmik 1, WS 2004/05, Folie 4-73 M. Philippsen