Technische Informatik für Ingenieure – WS 2010/2011 Übungsblatt Nr. 7 21. November 2010 Übungsgruppenleiter: Matthias Fischer Mouns Almarrani Rafał Dorociak Michael Feldmann Thomas Gewering Benjamin Koch Dominik Lüke Alexander Teetz Simon Titz Simon Oberthür Seite 1(7) Aufgabe 1: (Programm simulieren, Arrays) Finden Sie heraus, was der folgende Code tut: int[] a = { 42, 9, 23, 18, 7 }; for (int i = a.length - 1; i >= 0; i--) { for (int j = 0; j < i; j++) { if (a[j] > a[j + 1]) { int t = a[j + 1]; a[j + 1] = a[j]; a[j] = t; } } } Führen Sie dazu eine Simulation des Programms per Hand durch. Technische Informatik für Ingenieure t i j Seite 2(7) a[0] a[1] a[2] a[3] a[4] 42 9 23 18 7 9 4 0 9 42 23 18 7 23 4 1 9 23 42 18 7 18 4 2 9 23 18 42 7 7 4 3 9 23 18 7 42 7 4 4 9 23 18 7 42 3 0 9 23 18 7 42 18 3 1 9 18 23 7 42 7 3 2 9 18 7 23 42 7 3 3 9 18 7 23 42 2 0 9 18 7 23 42 7 2 1 9 7 18 23 42 7 2 2 9 7 18 23 42 7 1 0 7 9 18 23 42 7 1 1 7 9 18 23 42 7 0 0 7 9 18 23 42 7 -1 0 7 9 18 23 42 Das Programm sortiert das Array aufsteigend. Der Algorithmus wird BubbleSort genannt, weil große Zahlen wie Luftblasen aufsteigen. Dies ist im Beispiel bei der Zahl 42 zu sehen. Aufgabe 2: (Eindimensionale Arrays) Die Fibonacci-Folge ist eine unendlich lange Folge von nichtnegativen Zahlen (den so genannten Fibonacci-Zahlen). Sie ist durch folgendes rekursives Bildungsgesetzt definiert: f n = f n −1 f n−2 für n ≥ 2 mit den Anfangswerten f 0 = 0 und f 1=1 Schreiben Sie ein Programm, das vom Benutzer eine nichtnegative ganze Zahl n einliest und dann die Fibonacci-Folge bis zur n-ten Zahl berechnet ( f 0 ... f n , also n+1 Zahlen). Die Zahlen sollen zunächst in einem Array gespeichert und dann ausgegeben werden. Zum Beispiel wird für n=4 folgendes ausgegeben: 0 1 1 2 3 Technische Informatik für Ingenieure Seite 3(7) public class Fibonacci { public static void main(String[] args) { // Eingabe Out.print("Bis zur wievielten Zahl soll die" + " Fibonacci-Folge ausgegeben werden? "); int n = In.readInt(); if (n < 0) { Out.println("Die eingegebene Zahl ist negativ!"); return; } // Fibonacci-Folge berechnen int fibonacci[] = new int[n+1]; fibonacci[0] = 0; if (n >= 1) fibonacci[1] = 1; for (int i=2;i<=n;i++) { fibonacci[i] = fibonacci[i-1] + fibonacci[i-2]; } } } // Ergebnis ausgeben for (int i=0;i<=n;i++) { Out.print(fibonacci[i] + " "); } Technische Informatik für Ingenieure Aufgabe 3: Seite 4(7) (Datei schreiben, Arrays) Schreiben Sie ein Programm, das den Benutzer zwei Zahlen m und n eingeben lässt und dann die ersten m Vielfachen der Zahlen 1 bis n in eine Datei schreibt. In der ersten Zeile stehen die Vielfachen der Zahl 1, in der zweiten Zeile die Vielfachen von 2 und in der letzten Zeile die Vielfachen von n (1*n, 2*n, ..., m*n). Speichern Sie die ersten m Vielfachen zunächst in einem Array, das Sie dann in die Datei ausgeben. Für m=3 und n=4 würde beispielsweise folgendes in der Datei stehen: 1 2 3 4 2 4 6 8 3 6 9 12 Hinweis: Öffnen Sie die Datei zunächst mit Out.open("ein-mal-eins.txt"). Sie können dann mit Out.print und Out.println in die Datei schreiben. Schließen Sie die Datei zum Schluss mit Out.close(). Nachdem Sie das Programm zum ersten Mal ausgeführt haben, müssen Sie in Eclipse mit der rechten Maustaste auf das Projekt klicken und Refresh bzw. Aktualisieren auswählen. Die Datei wird dann im Projekt angezeigt. public class EinMalEins { public static void main(String[] args) { // Eingabe Out.print("Geben Sie m ein: "); int m = In.readInt(); Out.print("Geben Sie n ein: "); int n = In.readInt(); // Datei öffnen Out.open("ein-mal-eins.txt"); // Vielfache berechnen und in Datei speichern for (int i=1;i<=n;i++) { // Vielfache berechnen int vielfache[] = new int[m]; for (int j=1;j<=m;j++) vielfache[j-1] = j*i; // Vielfache in Datei schreiben for (int j=1;j<=m;j++) Out.print(vielfache[j-1] + " "); Out.println(); } // Datei schließen Out.close(); } } Technische Informatik für Ingenieure Aufgabe 4: Seite 5(7) (Datei lesen, mehrdimensionale Arrays) Eine Matrix von n*n Zahlen heißt magisches Quadrat der Ordnung n, wenn alle Zeileund Spaltensummen gleich sind. Bei besonderen magischen Quadraten ergibt auch die Summe der Zahlen auf jeder Diagonalen den gleichen Wert. Normalerweise verwendet man in solchen Quadraten jede Zahl von 1 bis n² genau einmal. Sie sollen ein Programm schreiben, das magische Quadrate überprüft. Lesen Sie dazu zunächst ein Zahlenquadrat aus einer Datei ein. Die erste Zahl in der Datei gibt die Ordnung n des Quadrats an. Danach folgen die n² Zahlen des Quadrats. Speichern Sie das eingelesene Quadrat in einem mehrdimensionalen Array. Prüfen Sie nun die Zeilen- und Spaltensummen und geben Sie aus, ob es sich um ein magisches Quadrat handelt. Zusätzlich soll ausgegeben werden, ob die Summe der Diagonalen ebenfalls passt und ob jede Zahl von 1 bis n² genau einmal vorkommt. Hinweis: Die Datei kann mit In.open("square1.txt") geöffnet werden. Danach kann man mit In.readInt() eine Zahl aus der Datei lesen. Vergessen Sie nicht die Datei zum Schluss mit In.close() zu schließen. public class MagicSquare { public static void main(String[] args) { // Zahlenquadrat einlesen In.open("square1.txt"); int n = In.readInt(); int square[][] = new int[n][n]; for (int i=0;i<n;i++) { for (int j=0;j<n;j++) { square[i][j] = In.readInt(); } } In.close(); // Zeilensummen testen int zeilensumme = 0; boolean zeilensummePasst = true; for (int i=0;i<n;i++) { int sum = 0; for (int j=0;j<n;j++) { sum += square[i][j]; } if (i == 0) zeilensumme = sum; else { if (zeilensumme != sum) { zeilensummePasst = false; Out.println("Zeile " + (i+1) + " hat die Summe " + sum + " statt " + zeilensumme); break; } } Technische Informatik für Ingenieure Seite 6(7) } if (zeilensummePasst) Out.println("Die Zeilensumme ist immer " + zeilensumme + "."); // Spaltensummen testen int spaltensumme = 0; boolean spaltensummePasst = true; for (int j=0;j<n;j++) { int sum = 0; for (int i=0;i<n;i++) { sum += square[i][j]; } if (j == 0) spaltensumme = sum; else { if (zeilensumme != sum) { spaltensummePasst = false; Out.println("Spalte " + (j+1) + " hat die Summe " + sum + " statt " + spaltensumme); break; } } } if (spaltensummePasst) Out.println("Die Spaltensumme ist immer " + zeilensumme + "."); //HINWEIS: Wenn die Zeilen- und Spaltensummen einheitlich // sind, ist immer spaltensumme==zeilensumme. // Deshalb wird das nicht zusätzlich geprüft. if (zeilensummePasst && spaltensummePasst) Out.println("Es handelt sich um ein magisches " + "Quadrat."); // Haupt- und Nebendiagonale prüfen int hauptdiagonale = 0; int nebendiagonale = 0; for (int i=0;i<n;i++) { hauptdiagonale += square[i][i]; nebendiagonale += square[i][n-i-1]; } if (hauptdiagonale == nebendiagonale && hauptdiagonale == zeilensumme) Out.println("Die Diagonalensumme ist ebenfalls " + hauptdiagonale + "."); else Out.println("Die Diagonalensummen sind " + hauptdiagonale + " und " + nebendiagonale); // vorkommende Zahlen prüfen boolean kommtZahlVor[] = new boolean[n*n]; boolean richtigeZahlen = true; for (int i=0;i<n;i++) { for (int j=0;j<n;j++) { int z = square[i][j]; if (z < 1 || z > n*n) { Out.println("Die Zahl " + z Technische Informatik für Ingenieure Seite 7(7) + " ist zu groß oder zu klein."); richtigeZahlen = false; break; } else if (kommtZahlVor[z-1]) { Out.println("Die Zahl " + z + " kommt mehrfach vor."); richtigeZahlen = false; break; } else { kommtZahlVor[z-1] = true; } } // Abbruch beim ersten Fehler if (!richtigeZahlen) break; } if (richtigeZahlen) Out.println("Jede Zahl von 1 bis n*n kommt genau " + "einmal vor."); } Datei } Zeilen- Spalten- Diago- 1 bis n² Kommentar summe summe nalen square1.txt 21 21 21 nein alles 7 square2.txt 10 --- 10 nein 4 mal 1 2 3 4 square3.txt 6 6 4 und 8 nein 1er und 2er Blöcke square4.txt 34 34 34 ja Yang-Hui-Quadrat square5.txt 15 15 15 ja Saturn-Siegel square6.txt 34 34 34 ja aus Dürers Kupferstich „Melencolia I“ square7.txt 34 34 34 ja pandiagonal (auch die gebrochenen Diagonalen haben dieselbe Summe)