Grundlagen der Programmierung –Teil1 Einheit III - 23. Okt. 2009 GDP DDr. Karl D. Fritscher basierend auf der Vorlesung “Grundlagen der Programmierung” von DI Dr. Bernhard Pfeifer Ausdrücke & Anweisungen In Java unterscheidet man zwischen Ausdrücken und Anweisungen: • Ausdruck: Ein Ausdruck ist in Java im einfachsten Fall eine Konstante oder eine Variable. Ausdrücke haben immer einen Wert, er auch oft als Rückgabewert bezeichnet wird Alles das, was einen Wert zurück liefert, stellt einen Ausdruck dar. durch Verknüpfung von Operanden durch Operatoren entsteht ein komplexer Ausdruck Ausdrücke & Anweisungen Anweisungen: Im Gegensatz zu Ausdrücken haben Anweisungen keinen Rückgabewert. Mann kann folgende Anweisungen unterscheiden: Leere Anweisung Anweisungen zur Deklaration von Variablen Ausdrucksanweisung Selektionsanweisung (if, switch) Iterationsanweisung (while, do, for) Sprunganweisungen (break, continue) Try - Anweisung Throw - Anweisung Synchronized - Anweisung Anweisungen • Eine Reihe von Anweisungen kann in einem Block zusammengefasst werden { Anweisung1; Anweisung2; } • Im Prinzip erlaubt die Blockanweisung eine Zusammenfassung von vielen Anweisungen zu einer einzigen geblockten (komplexen) Einzelanweisung. • Die leere Anweisung • ; ist die einfachste Anweisung und hat auf das laufende Programm keinerlei Effekt Anweisungen • Variablendeklaration • Syntax: Typname VariablenName; Typname VariablenName = Initialwert; • die Deklaration einer lokalen Variable gilt in Java als eine Anweisung. Sie darf überall erfolgen, wo auch eine andere Anweisung stehen dürfte. class Point Klassenname { Definition int x; Instanzvariablen der int y; Klasse Konstruktor mit Parametern x Point (int x, int y) und y Block { this.x = x; Block Zuweisung der Parameter this.y = y; } } this Referenz auf das aktuelle Objekt. Adressiert somit die Objektattribute (Instanzvariable) Anweisungen • Ausdrucksanweisungen • Syntax Ausdruck; • Ausdruckanweisungen dienen dazu, Ausdrücke in einem Anweisungskontext auszuführen. Sie werden erzeugt, indem man an den Ausdruck ein Semikolon anhängt. Ausdrucksanweisungen sind: Zuweisung a+=b; Inkrement oder Dekrement c++; Methodenaufruf System.out.println(„Hello“); Instanzerzeugung Auto bmw = new Auto(); Anweisungen • Verzweigungen • • erst aufgrund von Verzweigungen ist es möglich komplexe Programme zu erstellen. Die Verzweigung ist eine der wichtigsten Anweisungen überhaupt, da Entscheidungen gefällt und verschiedene Codezweige ausgeführt werden können. In Java existiert die if und if-else sowie die switch Anweisung Hunger ? nein GDP lernen ja Essen Die if Anweisung • Syntax if(ausdruck) anweisung; if(ausdruck) anweisung; else anweisung; • Zuerst wird der Ausdruck (ausdruck) ausgewertet. Die Anweisung (anweisung) wird genau dann ausgewertet , wenn der Ausdruck (ausdruck) true zurückgeliefert hat. Wird hingegen false zurückgeliefert, so wird nichts gemacht oder wie in der zweiten Anweisung der else Zweig ausgeführt 79 Dangling Else • In fast allen blockorientierten Programmiersprachen können durch die Else Anweisung Mehrdeutigkeiten entstehen. Dann ist es oft schwer möglich zu sagen zu welchem if das else gehört : if (a) if (b) dothis (); else dothat (); Zu welchem if gehört nun der else Zweig? • Der Else Zweig gehört immer zu der innersten Verzweigung (die noch nicht geschlossen wurde). Hätte man den Code richtig eingerückt, so wäre dies auch gleich klar ersichtlich: if (a) if (b) dothis else dothat (); (); 80 Switch- Anweisung Für eine Mehrfachselektion, d.h. eine Selektion mit mehreren Alternativen kann die switch-Anweisung verwendet werden: • Syntax switch (ausdruck) { case constant : anweisung; …… break; case constant : ……… default : ……… } • • Die mit dem Wortsymbol case eingeleiteten Konstanten mit nachfolgendem Doppelpunkt legen dabei so genannte Einsprungmarken für den Programmablauf fest. Zwischen dieses Einsprungsmarken müssen nicht unbedingt Anweisungen stehen. Außerdem sind auch die Abbruchanweisung (break) sowie die Marke default und die nachstehenden Anweisungen optional. 82 Switch-Anweisung • Syntax switch (ausdruck) { case constant : anweisung; …… break; case constant : ……… default : ……… } • Es handelt sich im switch Block um eine Folge von Anweisungen, von denen einige als Einsprungsmarken definiert sind. Es wird zunächst der Ausdruck ausgewertet, dessen Ergebnistyp byte, short, int oder char (auch enum ist erlaubt) sein muss. Daraufhin wird der Programmablauf genau an der case-Marke fortgesetzt, die mit der Auswertung übereinstimmt. Es wird der Code ausgeführt, bis auf eine break Anweisung gestoßen wird. Die break Anweisung bewirkt, dass die switch Anweisung verlassen wird. • Wird keine passende case Konstante gefunden, so wird bei der default Marke (sofern vorhanden) fortgesetzt. 82 Switch-Anweisung b = 5; ??? a b 1 20 2 20 3 20 4 40 5 0 83 Schleifen • In Java gibt es drei verschiedene Schleifenanweisungen. Diese werden wie folgt bezeichnet: • abweisende Schleife (while-Schleife) • nichtabweisende Schleife (do-while-Schleife) • Zählschleife (for-Schleife) 84 While-Schleife • • Die while Schleife while (ausdruck) anweisung; Zuerst wird der Ausdruck, der vom Typ boolean sein muss ausgewertet. Ist er true, wird die Anweisung ausgeführt, andernfalls wird mit der ersten Anweisung hinter der Schleife weitergemacht. Nachdem die Schleifenanweisung ausgeführt wurde, wird der Ausdruck erneut geprüft usw. 85 While-Schleife • Die while Schleife while (ausdruck) anweisung; public class Schleife1 { public static void main(String args[]) { int i=0; while (i<10) // Solange i < 10 … { i=i+1; System.out.println("Die Zahl ist: " + i); } } } 85 do-while-Schleife • Die do-while-Schleife do anweisung; while(ausdruck); • • Die do-while-Schleife arbeitet nichtabweisend. Dies bedeutet, dass sie zumindest einmal ausgeführt werden muss, denn erst nach dem ersten Durchlauf wird der Ausdruck geprüft. Die Schleife wird immer dann beendet, wenn der Ausdruck false ergibt 86 do-while-Schleife • Die do-while Schleife do anweisung; while(ausdruck); public class Schleife2 { public static void main(String args[]) { int i = 11; do Wird Schleife durchlaufen ?? { System.out.println("i = " + i); } while (i < 10); } } 86 for-Schleife • Die for-Schleife for (init; test; update) anweisung; • Der Kopf der for Schleife besteht aus drei Ausdrücken - jeder ist optional • Der init Ausdruck wird einmal vor dem Start der Schleife aufgerufen. Dort werden Initialisierungen durchgeführt. Der init Teil darf aus mehreren Ausdrücken bestehen, wenn die einzelnen Teilausdrücke durch Kommata getrennt sind. Fehlt dieser Teil, so wird keine Initialisierung durchgeführt. • Der init Teil darf auch Variablendeklarationen enthalten (Schleifenzähler) • Der test Teil bildet den zu testenden Ausdruck. Analog zur while Schleife wird dieser zu Beginn der Schleife ausgeführt. Ist der Ausdruck true wird in die Schleife gegangen. Fehlt der Testausdruck wird vom Compiler true eingesetzt. 87 for-Schleife • Die for-Schleife for (init; test; update) anweisung; • Der update Ausdruck dient dazu, den Schleifenzähler zu verändern. Er wird nach jedem Schleifendurchlauf ausgewertet. Fehlt dieser Ausdruck, so wird nichts gemacht. 88 for-Schleife public class LoopSample { public static void main (String [] args) { for (int i = 0; i < 4; i++) { for (int j = 0; i < 4; j++) { System.out.println(“Ergebnis:” + (i+1) * (j+1)); } } Was passiert hier ?? } } Test-Ausdruck in 2. Schleife führt zu Endlosschleife!! Typischer copy-paste bug!! Korrekt: for (int j = 0; j < 4; j++) 88 for-Schleife public class LoopSample { public static void main (String [] args) { int [][] multiTab = new int [4][4]; for (int i = 0; i < 4; i++) { for (int j = 0; j < 4; j++) { multiTab[i][j] = (i+1) * (j+1); } } } } i 0 1 2 3 j 0,1,2,3 0,1,2,3 0,1,2,3 0,1,2,3 multiTab 1,2,3,4 2,4,6,8 3,6,9,12 4,8,12,16 i/j 0 1 2 3 0 1 2 3 4 1 2 4 6 8 2 3 6 9 12 3 4 8 12 16 88 Die erweiterte for-Schleife • Mit Java 5.0 (1.5) wurde die for-Schleife um eine syntaktische Variante erweitert, die den Umgang mit listenartigen Strukturen stark erleichtert. • Diese Variante ist auch als foreach bekannt for (formalparameter anweisung; : ausdruck) • Der »formalparameter« ist dabei eine aus Datentyp und Variablenname bestehende Parameterdeklaration (der Art java.lang.Object obj) • »ausdruck« ist eine Instanz oder ein Ausdruck des Typs java.lang.Iterable oder ein Array. 90 Die erweiterte for-Schleife • Wendet man die erweiterte for-Schleife auf Arrays an, so ist wie folgt vorzugehen: int[] a = {1,2,3,4,5}; for(int element : a){ //”Für jedes Element aus a … System.out.println (element); } äquivalent zu: int[] a = {1,2,3,4,5}; for (int i = 0; i < a.length; i++){ System.out.println (a[i]); } 91 Labels, Break & continue • In Java gibt es zwei verschiedene Möglichkeiten, die normale Auswertungsreihenfolge in einer Schleife mit den Sprunganweisungen break und continue zu verändern: Taucht innerhalb der Schleife ein break auf, wird die Schleife verlassen, und das Programm wird mit der ersten Anweisung nach der Schleife fortgesetzt. Taucht ein continue auf, so springt das Programm an das Ende des Schleifenrumpfs und beginnt mit der nächsten Iteration. • Darüber hinaus gibt es in Java die Möglichkeit Schleifen mit Labels zu versehen. Zusätzlich zu den Anweisungen break und continue gibt es daher in Java noch break label; und continue label; - In diesem Fall wird zum definierten Label gesprungen bzw. zur ersten Anweisung nach dem definierten Label. 89 Break & continue Beispiel gelabeltes break: loop1: for (int i=0; i<100; ++i) { for (int j=0; j<100; ++j) { if (A[i][j] > 42) { break; } if (A[i][j] == 0) { break loop1; } } } loop1: for (int i=0; i<100; ++i) { Beispiel for (int j=0; j<100; ++j) { gelabeltes if (A[i][j] > 42) { continue: continue loop1; } if (A[i][j] == 0) { continue; } } } 89 assert - Anweisung • • • • Die assert Anweisung assert ausdruck1 [ : ausdruck2 ]; Diese Anweisung dient dazu, an einer bestimmten Stelle im Programm einen logischen Ausdruck (ausdruck1) zu platzieren, von dem der Programmierer annimmt, dass er stets wahr ist. In diesem Fall fährt das Programm mit der nächsten Anweisung fort, andernfalls wird eine Ausnahme des Typs AssertionException ausgelöst (bzw. der optionale Ausdruck 2 als Fehlermeldung ausgegeben) Ein solcher Ausdruck wird auch als Invariante bezeichnet, denn er bleibt unverändert true, solange das Programm korrekt funktioniert. Eine assert Anweisung erlaubt den Zustand eines Programmes zu überprüfen und sicherzustellen, dass die prinzipielle Forderung für einen korrekten Programmablauf eingehalten wird. BEACHTE: Assertions sind in JAVA standardmässig deaktiviert. Aktiviertung durch Parameter –ea zB: Java –ea HelloWorld 92 assert - Anweisung • Die assert Anweisung assert ausdruck1 [ : ausdruck2 ]; • Beispiel: int[] a = {1,2,3,4,10}; for(int element : a){ //”Für jedes Element aus a … assert (el<=5) : ”Zahl muss kleiner oder gleich 5 sein!!”; System.out.println (element); } 92 assert - Anweisung • Ein assert kann natürlich auch mit einem if simuliert werden. Assert hat jedoch folgende Vorteile Code ist kürzer es ist sofort zu erkennen, dass es sich um einen Korrektheitscheck und nicht um ein logisches Programmkonstrukt handelt Assertions können zur Laufzeit wahlweise an als auch ausgeschaltet werden