Lösung - Universität Paderborn
Transcription
Lösung - Universität Paderborn
Technische Informatik für Ingenieure – WS 2010/2011 Musterlösung Übungsblatt Nr. 4 1. 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(5) Aufgabe 1: (BNF, Grammatik entwickeln) Ziel dieser Aufgabe ist den Entwurf einer Grammatik zu üben. Wir überlegen uns zuerst, wie die Sprache aussieht und entwickeln anschließend eine Grammatik, die syntaktisch korrekte Worte aus der Sprache erzeugt. Worte der Sprache sind Vortragstermine an der Universität Paderborn: Ein Vortragstermin besteht aus Datum, Zeit und Raum, die jeweils durch ein Komma „,“ getrennt sind: • Ein Datum besteht aus einer ein- bis zweiziffrigen Tagesangabe, gefolgt von einem Punkt, gefolgt von einer ein bis zweiziffrigen Monatsangabe, gefolgt von einer vierziffrigen Jahresangabe. • Die Zeitangabe besteht aus einer ein- bis zweiziffrigen Stundenangabe, gefolgt von einem „:“, gefolgt von einer zweiziffrigen Minutenangabe, gefolgt von der Zeichenkette „Uhr“. • Die Raumangabe der Universität Paderborn besteht aus der Zeichenkette „Raum“, gefolgt von einem einzelnen Buchstaben aus der Menge {A, B, C, D, E, F, O, N, W} zur Spezifizierung des Gebäudeteils (wir betrachten hier nicht alle Gebäude), gefolgt von einer Ziffer für das Stockwerk (es gibt maximal 8 Stockwerke), gefolgt von einem Punkt „.“, gefolgt von einer dreiziffrigen Raumangabe. Beispiele: Raum F2.301, E2.310, E2.316, F1.201. Ein Vortragstermin sieht also so aus: 2.11.2010, 7:30 Uhr, Raum E1.130 Lösung: <Termin> ::= <Datum> , <Zeit> Uhr, Raum <Raum> <Zeit> ::= <Stunde> : <Minute> <Stunde> ::= [1] <Ziffer> | 2 <NullBisDrei> <Minute> ::= <NullBisFünf> <Ziffer> <Datum> ::= <Tag> . <Monat> . <Jahr> Technische Informatik für Ingenieure Seite 2(5) <Jahr> ::= <Ziffer> <Ziffer> <Ziffer> <Ziffer> <Monat> ::= <Ziffer außer Null> | 1 <NullBisZwei> <Tag> ::= <Ziffer außer Null> | <EinsBisZwei> <Ziffer> | 30 | 31 <Raum> ::= <Gebäude> <Stockwerk> . <RaumNr> <RaumNr> ::= <Ziffer> <Ziffer> <Ziffer> <Ziffer> ::= 0 | <Ziffer außer Null> <EinsBisZwei> ::= 1 | 2 <NullBisZwei> ::= 0 | 1 | 2 <NullBisDrei> ::= 0 | 1 | 2 | 3 <NullBisFünf> ::= 0 | 1 | 2 | 3 | 4 | 5 <Gebäude> ::= A | B | C | D | E | F | O | N | W <Stockwerk> ::= 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 <Ziffer außer Null> ::= 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 Bemerkung: Die dargestellte Grammatik löst zwar das Problem, sie ist jedoch stellenweise sehr „aufwendig“. Einfacher gibt man eine kleine endliche Anzahl an Alternativen durch Aufzählung an, also: <Tag> ::= 1 | 2 | 3 | … | 30 | 31 <Monat> ::= 1 | 2 | 3 | … | 11 | 12 <Stunde> ::= 1 | 2 | 3 | … | 23 | 24 <Minute> ::= 01 | 02 | 03 | … | 59 | 60 Aufgabe 2: (BNF, Grammatik überprüfen) Ziel dieser Aufgabe ist das Überprüfen einer Grammatik zu üben. 1. Um zu bestimmen, ob ein gegebenes Wort zu der von der Grammatik erzeugten Sprache gehört, ist eine Folge von Ableitungen anzugeben, mit der das Wort ausgehend von dem Startzeichen erzeugt werden kann. 2. Um zu zeigen, dass ein gegebenes Wort (z.B. „a+bc+a“) nicht zu der von der Grammatik erzeugten Sprache gehört, reicht es nicht aus, eine Folge von Ableitungen anzugeben, die das Wort nicht erzeugt. Statt dessen ist eine Begründung anzugeben, warum das gegebene Wort nicht erzeugt werden kann (z.B. „Die terminalen Zeichen b und c können nicht unmittelbar aufeinander folgen, da je zwei der als Summand erzeugten Zeichen durch das terminale Zeichen + getrennt sein müssen.“). Technische Informatik für Ingenieure Seite 3(5) Sei die folgende Grammatik gegeben: Terminale: {a, b} Nichtterminal: {S} Produktionen: P1: S ::= aSa P2: S ::= bSb P3: S ::= a P4: S ::= b Alle Ableitungen fangen mit dem Nichtterminal S (Startsymbol) an. Welche der folgenden Worte sind von dieser Grammatik erzeugbar? abababa abababb ababbaaba aabbbabbbaa ababbaba Wie beschreibt man allgemein die Ausdrücke, die von dieser Grammatik erzeugt werden? Lösung: abababa wird durch die Grammatik erzeugt: S → aSa → abSba → abaSaba → abababa abababb kann nicht erzeugt werden, da wegen der Produktionen P1, P2 die erzeugbaren Wörter symmetrisch sein müssen. Am Anfang ein „a“ und am Ende ein „b“ kann nicht erzeugt werden. ababbaaba kann auch nicht erzeugt werden, da wegen P1, P2 die Wörter symmetrisch sein müssen. aabbbabbbaa wird durch die Grammatik erzeugt: S → aSa → aaSaa → aabSbaa → aabbSbbaa → aabbbSbbbaa → aabbbabbbaa ababbaba kann nicht erzeugt werden, da jedes mit der Sprache erzeugte Word wegen der Produktionen P1, P2 eine ungerade Länge besitzen muss. Beschreibung der von der Grammatik erzeugten Sprache Die durch die Grammatik erzeugbaren Wörter besitzen wegen der Produktionen P1, P2 eine ungerade Länge. Die erste Worthälfte ist eine beliebige Folge der Zeichen „a“ und „b“. Die zweite Worthälfte ist die umgekehrte Reihenfolge der Zeichen der ersten Worthälfte. Zwischen beiden Worthälften steht ein „a“ oder „b“. Die Grammatik erzeugt Palindrome mit ungerader Wortlänge aus den Buchstaben „a“ und „b“. Technische Informatik für Ingenieure Aufgabe 3: Seite 4(5) (Bedingte Anweisungen) Ein Jahr ist ein Schaltjahr, wenn die Jahreszahl durch 4, aber nicht durch 100 teilbar ist. Ist die Jahreszahl aber durch 400 teilbar, dann ist das betreffende Jahr doch ein Schaltjahr. Schreiben Sie nun ein Java-Programm, das eine Jahreszahl von der Tastatur einliest und ausgibt, ob es sich bei dem eingegebenen Jahr um ein Schaltjahr handelt oder nicht. Erstellen Sie dazu eine neue Klasse namens „Schaltjahr“ in ihrem TIFI-Projekt (Rechte Maustaste auf (default package) → New → Class): In dem erscheinenden Dialog geben Sie als Name „Schaltjahr“ ein, setzen das Häckchen vor „public static void main(String[] args)“ und bestätigen mit „Finish“: Verwenden Sie für die Ein- und Ausgabe die Ausdrücke In.readInt() sowie Out.print(“text“) bzw. Out.println(“text mit Zeilenumbruch“). Sollte das Ergebnis nicht Ihren Erwartungen entsprechen, debuggen Sie das Programm wie in Aufgabe 2 beschrieben. Hinweis: Verwenden Sie den Operator % (modulo), um herauszufinden, ob eine Zahl durch eine andere teilbar ist. Der Ausdruck 5 % 3 wird als der Rest der ganzzahligen Division 5 / 3 ausgewertet; das Ergebnis ist in diesem Fall 2. Für eine ganzzahlige Variable n ist der Ausdruck n % 4 == 0 genau dann wahr, wenn n durch 4 teilbar ist. Technische Informatik für Ingenieure Seite 5(5) Lösung: Es ist hilfreich, sich vor der Programmierung Gedanken über die Struktur des Programms zu machen. Zum Beispiel könnte man ein Flussdiagramm zeichnen: [ja] [ja] Jahr durch 100 teilbar [nein] Jahr durch 400 teilbar [ja] Ausgabe: Schaltjahr Jahr durch 4 teilbar [nein] [nein] Ausgabe: kein Schaltjahr Ausgabe: Schaltjahr Ausgabe: kein Schaltjahr Das Java-Programm, welches bestimmt, ob ein Jahr ein Schaltjahr ist, könnte wie folgt aussehen: public class Schaltjahr { public static void main(String[] args) { // Jahr einlesen Out.print("Bitte geben Sie das Jahr ein:"); int jahr = In.readInt(); // Jahr prüfen if (jahr % 4 == 0) { if (jahr % 100 == 0) { if (jahr % 400 == 0) { Out.println("Es ist ein Schaltjahr."); } else { // durch 4 und 100, aber nicht durch 400 teilbar Out.println("Es ist kein Schaltjahr."); } } else { // durch 4, aber nicht durch 100 teilbar Out.println("Es ist ein Schaltjahr."); } } else { // nicht durch 4 teilbar Out.println("Es ist kein Schaltjahr."); } } } Hinweis: Im Laufe der Vorlesung werden Sie weitere Operatoren kennen lernen, mit deren Hilfe Sie mehrere Boolesche Ausdrücke zusammenfassen und das Programm wie folgt abkürzen können: // Jahr pruefen if ((jahr % 4 == 0 && jahr % 100 != 0) || jahr % 400 == 0) { Out.println("Es ist ein Schaltjahr."); } else { Out.println("Es ist kein Schaltjahr."); }