Programm-Ablauf. int main() // Beispiel- Struktur eines Programmes. prepare_everything(); read_input(); calculate_result(); write_output();

Ähnliche Dokumente
Institut für Programmierung und Reaktive Systeme. Java 2. Markus Reschke

Kapitel 4. Programmierkurs. Datentypen. Arten von Datentypen. Wiederholung Kapitel 4. Birgit Engels, Anna Schulze WS 07/08

Java Einführung VARIABLEN und DATENTYPEN Kapitel 2

4.2 Gleitkommazahlen. Der Speicherbedarf (in Bits) ist üblicherweise. In vielen Anwendungen benötigt man gebrochene Werte. Physikalische Größen

Wertebereich und Genauigkeit der Zahlendarstellung

Variablen. CoMa-Übung VIII TU Berlin. CoMa-Übung VIII (TU Berlin) Variablen / 15

Projekt 3 Variablen und Operatoren

Java I Vorlesung Imperatives Programmieren

1. Referenzdatentypen: Felder und Strings. Referenz- vs. einfache Datentypen. Rückblick: Einfache Datentypen (1) 4711 r

1. Referenzdatentypen: Felder und Strings

Grundlagen der Informatik 2. Typen

Programmierkurs C++ Variablen und Datentypen

Noch für heute: primitive Datentypen in JAVA. Primitive Datentypen. Pseudocode. Dezimal-, Binär- und Hexadezimalsystem. der logische Typ boolean

Die Programmiersprache C

Unterlagen. CPP-Uebungen-08/

JAVA-Datentypen und deren Wertebereich

Das diesem Dokument zugrundeliegende Vorhaben wurde mit Mitteln des Bundesministeriums für Bildung und Forschung unter dem Förderkennzeichen

Einstieg in die Informatik mit Java

Welche Informatik-Kenntnisse bringen Sie mit?

Algorithmen zur Datenanalyse in C++

2. Programmierung in C

Einheit Datentypen in der Programmiersprache C Schwerpunkt: Elementare (arithmetische) Datentypen

Java - Zahlen, Wahrheitswerte und Zeichen. Leibniz Universität IT Services Anja Aue

Einstieg in die Informatik mit Java

2.5 Primitive Datentypen

Kapitel 3. Grunddatentypen, Ausdrücke und Variable

Einführung in die Informatik: Programmierung und Software-Entwicklung, WS 12/13. Kapitel 3. Grunddatentypen, Ausdrücke und Variable

FACHHOCHSCHULE AUGSBURG Hochschule für Technik, Wirtschaft und Gestaltung

float: Fließkommazahl nach IEEE 754 Standard mit 32 bit

Einführung in die C-Programmierung

Sprachkonstrukte. Einführung in Java. Folie 1 von Mai Ivo Kronenberg

Elementare Konzepte von

Einführung in C. EDV1-04C-Einführung 1

Prof. Dr. Oliver Haase Karl Martin Kern Achim Bitzer. Programmiertechnik Operatoren, Kommentare, Ein-/Ausgabe

Programmiertechnik Skalare Typen,Variablen, Zuweisungen

C++ Notnagel. Ziel, Inhalt. Programmieren in C++

Kapitel 3: Variablen

Java - Zahlen, Wahrheitswerte und Zeichen. Leibniz Universität IT Services Anja Aue

Operatoren für elementare Datentypen Bedingte Anweisungen Schleifen. Operatoren für elementare Datentypen Bedingte Anweisungen Schleifen

JavaScript. Dies ist normales HTML. Hallo Welt! Dies ist JavaScript. Wieder normales HTML.

Einführung in den Einsatz von Objekt-Orientierung mit C++ I

Grundlagen der OO- Programmierung in C#

Schleifen in C/C++/Java

Einstieg in die Informatik mit Java

Javaprogrammierung mit NetBeans. Variablen, Datentypen, Methoden

Elementare Datentypen in C++

Schachtelung der 2. Variante (Bedingungs-Kaskade): if (B1) A1 else if (B2) A2 else if (B3) A3 else if (B4) A4 else A

Modellierung und Programmierung 1

Programmierung mit C Zeiger

Integer Integer Integer (Voreinstellung) Integer Gleitkomma Gleitkomma leer/unbestimmt Integer ohne Vorzeichen Integer (explizit) mit Vorzeichen

3. Java - Sprachkonstrukte I

Kapitel 4: Elementare Konzepte von Programmiersprachen. Variablen Referenzen Zuweisungen

2 Einfache Rechnungen

Programmierkurs C++ Lösungen zum Übungsblatt 3. Nils Eissfeldt und Jürgen Gräfe. 2. November Aufgabe 5

5.1 Mehr Basistypen. (Wie viele Werte kann man mit n Bit darstellen?)

Einstieg in die Informatik mit Java

3. Datentypen, Ausdrücke und Operatoren

Numerische Datentypen. Simon Weidmann

Kapitel 2: Python: Ausdrücke und Typen. Grundlagen der Programmierung 1. Holger Karl. Wintersemester 2016/2017. Inhaltsverzeichnis 1

Programmieren in C. C Syntax Datentypen, Operatoren und Kontrollstrukturen. Prof. Dr. Nikolaus Wulff

3. Datentypen, Ausdrücke und Operatoren

Einführung in die Programmierung WS 2009/10. Übungsblatt 5: Typen, Variablen und einfache Methoden in Java

RO-Tutorien 15 und 16

Algorithmen & Programmierung. Ausdrücke & Operatoren (1)

Einstieg in die Informatik mit Java

Einführung in die Informatik für Hörer aller Fakultäten II. Andreas Podelski Stephan Diehl Uwe Waldmann

Einstieg in die Informatik mit Java

Übersicht. Peter Sobe 1

Grundlagen der Programmierung

Primitive Datentypen und Felder (Arrays)

Programmieren in C. Eine Einführung in die Programmiersprache C. Prof. Dr. Nikolaus Wulff

Programmieren in C / C++ Grundlagen C 2

Deklarationen in C. Prof. Dr. Margarita Esponda

Die Sprache C# Datentypen, Speicherverwaltung Grundelemente der Sprache. Dr. Beatrice Amrhein

Repräsentation von Daten Binärcodierung von rationalen Zahlen und Zeichen

RO-Tutorien 3 / 6 / 12

Moderne C-Programmierung

Grundlagen der Informatik Ergänzungen WS 2007/2008 Prof. Dr. Rainer Lütticke

Informationsverarbeitung im Bauwesen

Motivation und Überblick

Übung zur Vorlesung Wissenschaftliches Rechnen Sommersemester 2012 Auffrischung zur Programmierung in C++, 1. Teil

Arbeitsblätter für die Lehrveranstaltung OOP JAVA 1

Ein erstes Java-Programm

Programmieren I. Kapitel 5. Kontrollfluss

Grundelemente von C++

JAVA BASICS. 2. Primitive Datentypen. 1. Warum Java? a) Boolean (logische Werte wahr & falsch)

Folgen und Funktionen in der Mathematik

Primitive Datentypen, Eingaben, Kontrollstrukturen und Methodendeklaration

Physische Datenstrukturen

Transkript:

Programm-Ablauf Alle betrachteten Programmiersprachen C, C++, Java führen Anweisungen in der Reihenfolge aus, in der diese im Quellcode stehen. Dieser normale Ablauf kann geändert werden durch: 1) Sprunganweisungen im erweiterten Sinn. Durch diese erfolgt die weitere Programmausführung an der anzuspringenden Stelle. Beispiele sind etwa die goto Anweisung in C/C++, jeder Funktionsaufruf, jedes return-statement usw. Funktionsaufrufe erkennt man in diesen Sprachen an den runden Klammern () hinter der aufgerufenen Funktion: sin(1.0). Ein Funktionsname ohne Klammern bewirkt keinen Funktionsaufruf, ist also "toter Code": sin; 2) Schleifen: Diese werden so oft wiederholt, wie eine Kontroll-Bedingung wahr ist. Beispiele in C/C++/Java sind while, do while, for 3) Bedingte Anweisungen: Diese Anweisungen werden nur beim Zutreffen einer Bedingung ausgeführt. Beispiele sind if, if else, switch case Die Programm-Ausführung startet in C und C++ mit der Funktion main(). Diese muss daher in jedem C/C++ - Programm genau einmal vorhanden sein (bei Java ist das ein wenig anders gelöst). Wenn diese Funktion endet (bei der schließenden geschwungenen }-Klammer oder bei einer return-anweisung im Inneren), dann endet auch das ganze Programm. Man kann alles in diese main-funktion hineinpacken (bei längeren Programmen unübersichtlich) oder aber aus dieser Funktion heraus aufrufen. Ein kleines Beispiel: int main() // Beispiel- Struktur eines Programmes { prepare_everything(); read_input(); calculate_result(); write_output(); return EXIT_SUCCESS; }

Datentypen, Objekte Zur Programmausführung werden fast immer Datenobjekte benötigt. Bei der Definition von variablen Objekten muss man entweder deren Datentyp explizit angeben oder aber der Typ wird als auto spezifiziert und muss vom Compiler anhand der Syntax automatisch erkannt werden (ab C++11). Konstante Objekte erkennt der Compiler immer an der Schreibweise. Die Objekte unterteilt man in 1) Variable Objekte, Variable: Diese Objekte lassen sich verändern. Sie müssen einen Namen haben, unter dem sie angesprochen werden können. C/C++ reserviert den Speicherplatz für definierte Variable vollautomatisch und gibt diesen auch wieder frei. 2) Konstante: Diese Objekte lassen sich nicht verändern, sie belegen auch keinen Speicherplatz, sondern sind nur im Programmcode enthalten. 3) konstante Objekte (erkennbar am const Schlüsselwort): Diese lassen sich genau einmal verändern, nämlich bei der Definition. Diesen Typ verwendet man gerne, um Programme an bestimmte Situationen anzupassen. Das Original-C konnte das noch nicht und musste stattdessen Präprozessor-Makros verwenden. Datentypen: Jede Programmiersprache stellt bestimmte Datentypen wie z.b. Zeichenketten = Strings, ganze Zahlen, Gleitkomma-Zahlen etc. zur Verfügung. Je nach Ausrichtung sind auch komplexe Zahlen, Vektoren und Matrizen usw. vordefiniert (z.b. Fortran als Mathematik-Sprache). C, C++ und Java sind Allround-Sprachen und definieren nur das Allernötigste vor. Objektorientierte Sprachen gestatten es, fehlende Datentypen selbst zu definieren und damit die Sprache zu erweitern. Bezeichner, Namen Variable, Funktionen, selbstdefinierte Datentypen, Makros usw. müssen einen Namen oder Bezeichner haben, der folgenden Regeln genügt: 1) Namen dürfen aus Buchstaben, Ziffern und Unterstrich bestehen: falsch: a-z (Bindestrich nicht erlaubt), x.h (Punkt!) 2) Namen dürfen NICHT mit einer Ziffer beginnen 3) Klein- und Großschreibung wird unterschieden 4) Namen dürfen beliebig lang sein (C beachtet nur die ersten 31 Zeichen, C++ sehr viel mehr, sicherlich >1000 Zeichen) 5) Namen für Templates in C++ (und nur diese) dürfen/müssen auch die Zeichen < und > enthalten. 6) Namen gelten immer nur in dem Block (von {} eingeschlossen), in dem sie definiert sind. Ein Name außerhalb aller Blöcke gilt global im ganzen Programm. richtig: x234_2, Meine_Oma

Datentypen für ganze Zahlen In Standard C/C++ gibt es die Ganzzahltypen char (phonetisch TSCHAR), short (kurz für short int), int, long (kurz für long int), long long (kurz für long long int). Diese unterscheiden sich in der Anzahl der Bits (= binäre Ziffer, also nur die Werte 0 oder 1). Je mehr Bits einem Typ zugeordnet sind, desto größere Zahlen lassen sich darstellen. Jeder dieser Datentypen enthält auch negative Zahlen, und zwar gleich viele wie nichtnegative! ES GIBT KEINE VERBINDLICHEN REGELN für die Bit-Anzahl in C/C++! es gilt nur: Datenbits!) char <= short <= int <= long <= long long (im Sinne von Weit verbreitet ist z.b. folgendes Schema: char: 8 Bit: Werte von -128 bis 127 short: 16 Bit: Werte von ca. -32000 bis 32000 ( -2 15 bis 2 15-1) int: 32 Bit: Werte von -2 Mrd bis 2 Mrd ( -2 31 bis 2 31-1) long: -2 63 bis 2 63-1) long long: auch 64 oder gar 128 Bits Dennoch DARF MAN NICHT DAVON AUSGEHEN, dass es immer so sein muss. Manche Systeme haben int und long mit 32 Bit, manche int und long mit 64 Bit definiert. Hier geht Java einen anderen Weg, da hier die Bitzahlen eindeutig definiert sind: byte: 8 Bit: Werte von -128 bis 127: - (2 hoch 7) bis (2 hoch 7)-1 short: 16 Bit: Werte von ca. -32000 bis 32000: - (2 hoch 15) bis (2 hoch 15)-1 int: 32 Bit: Werte von -2 Mrd bis 2 Mrd: - (2 hoch 31) bis (2 hoch 31)-1 long: 64 Bit: Werte von - (2 hoch 63) bis (2 hoch 63)-1 Der Datentyp char ist in Java immer 16 Bits breit, aber kein numerischer Datentyp Alle diese Typen gibt es auch unsigned (gleiche Bitanzahl, aber nur positive Werte oder 0), wir haben also auch unsigned char, unsigned short (int), unsigned int, unsigned long (int), unsigned long long (int) unsigned 8 Bit: Werte von 0 bis 255: 0 bis 2 8-1 unsigned 16 Bit: Werte von ca. 0 bis 65000 (0 bis 2 16-1) unsigned 32 Bit: Werte von 0 bis 4 Mrd (0 bis 2 32-1) unsigned 64 Bit (0 bis 2 64-1) Portabel Programmieren in C/C++: Wenn man für ein Programmprojekt unbedingt Ganzzahlen mit einer ganz bestimmten Bitanzahl verwenden muss (z.b. IPv4-Adressen sind

immer 32 Bit lang), sollte man nicht einen Standardtyp wie int verwenden, weil dessen Zahlenumfang nicht fixiert ist. Die Norm C99 definiert neue Ganzzahl-Datentypen für C (und damit auch für C++), die eine garantierte Länge haben (z.b. int32_t für 32-bit Integer, uint64_t für 64-bit unsigned Integers usw.). Diese Typen sind im Headerfile <stdint.h> für C und im Headerfile <cstdint> für C++ definiert. Um die neuen Integertypen zu verwenden, muss man nur diese Headerdatei inkludieren. Weitere Ganzzahltypen sind für diverse Zwecke in verschiedenen Headern vordefiniert. So gibt es in C++ auch die Typen: std::size_t (z.b. in cstdlib definiert) std::streamsize (ios) std::time_t (ctime) Diese entsprechen immer einem der Standardtypen, allerdings kann es von der Hardware (32-Bit CPU oder 64-Bit CPU) und vom Betriebssystem abhängen (z.b. ist std::size_t manchmal als unsigned int, manchmal als unsigned long definiert!). Zum Rechnen mit den Ganzzahltypen stehen die arithmetischen Standard- Rechenoperationen + (Addition), - (Vorzeichen bzw. Subtraktion), * (Multiplikation), / (Division), sowie % (Divisionsrest) zur Verfügung. Sie liefern immer ein Ganzzahlergebnis vom selben Typ: 1 + 1 -> 2 7 / 4 -> 1 (Achtung!) 17 % 3 -> 2 (17 hat bei Division durch 3 den Rest 2) -5 % 3 -> -2 (Divisionsreste von negativen Zahlen sind negativ) Überlauf: Manchmal wird ein Ergebnis zu groß für einen Datentyp (meistens bei der Multiplikation). Hier kommt es zu einem falschen Ergebnis, ohne dass es eine Warnung dafür gibt! Datentypen für Gleitkommazahlen: Für solche Zahlen stehen die Datentypen float (einfache Genauigkeit), double (doppelte Genauigkeit) und long double (wird fast nie verwendet) zur Verfügung. float hat etwa 7 signifikante Stellen, double ca. 14. Dabei handelt es sich nicht um Nachkommastellen, die Zahlen werden intern immer im wissenschaftlichen Format mit einer Mantisse (mit der angegebenen Stellenzahl) und einem Exponenten gespeichert. Die Grundrechnungsarten +,-,*, / für Gleitkommazahlen erzeugen fast immer Rundungsfehler, aber KEINE Überläufe. Manchmal ist das Ergebnis einer Rechenoperation ungültig (z.b.

Division durch 0 oder Wurzel aus einer negativen Zahl etc.). Hier kann man oft einstellen, ob das Programm mit einer Fehlermeldung abbricht oder ob es mit speziellen ungültigen Zahlen weiterrechnet. Solche sind: NaN, nan: Not a Number Infinity, inf: Unendlich Mit welchem Typ wird eine Grundrechnungsart durchgeführt? C++ hat einige Regeln dazu, hier sind die wichtigsten: 1) Sind beide Operanden Gleitkommatypen, wird mit dem größeren der beiden Typen gerechnet (long double > double > float)und der andere Operand konvertiert. 2) Ist ein Operand ein Gleitkommatyp, der andere ein Ganzzahltyp, so wird mit dem Gleitkommatyp gerechnet und der Ganzzahltyp vorher konvertiert. 3) Sind beide Operanden Ganzzahltypen <= int, so wird mit int gerechnet und (wenn nötig), beide Operanden zu int konvertiert. 4) Ist ein Operand ein unsigned int, und der andere Operandentyp <= unsigned int, wird mit unsigned int gerechnet und der andere Operand in unsigned int konvertiert. Bei Vergleichsoperatoren und bei manchen arithmetischen Operationen geht das manchmal schief! Der Compiler warnt daher zu Recht, wenn ein unsigned int mit einem signed Datentyp verglichen wird!) 5) Regeln wie 3) und 4) gelten sinngemäß, wenn man int durch long oder long long ersetzt und wenigstens ein Operand diesen Typ hat. double / float -> double (Regel 1) int / float -> float (Regel 2) int / int -> int (Regel 3) char / short -> int (Regel 3) unsigned / unsigned -> unsigned (Regel 4) unsigned / char -> unsigned (oder Katastrophe!) (Regel 4) long / int -> long (Regel 5) Warnungsbeispiel: unsigned one = 1; // das gefährliche Duo: unsigned int minus_one = -1; // mit einem signed, der negativ ist if (minus_one > one) // und jetzt ein Vergleich: Autsch cout << minus_one << > << one << \n ; Zusammengesetzte Formeln: Diese werden in einzelne Rechenoperationen aufgeteilt und diese einzeln nach vorigen Regeln behandelt:

int + char + long -> (int + char) + long -> (int + int) + long -> int + long -> long + long -> long Beachte hier, dass wirklich JEDE Operation einzeln betrachtet wird. Es könnte also durchaus bei der ersten Addition (int + int) ein Überlauf auftreten, der bei der durchgängigen Rechnung mit long nicht aufgetreten wäre. Dennoch wird diese erste Addition mit int- Daten berechnet und erst das (möglicherweise falsche übergelaufene) Ergebnis in long umgewandelt. Das Assoziativgesetz gilt für diese Arithmetik NICHT: ( 2'000'000'000 + 2'000'000'000 ) + 0L ist meist etwas anderes als 2'000'000'000 + ( 2'000'000'000 + 0L ) Datentyp für Wahrheitswerte C++ kennt dazu den Datentyp bool, der die Werte true oder false annehmen kann. Beide Wahrheitswerte gestatten eine automatische Konvertierung in einen int, und zwar wird true in 1 und false in 0 konvertiert (C-kompatibel). In C (und damit auch in C++) gilt aber auch jeder numerische Ausdruck, der nicht 0 ist, als wahr und der Ausdruck 0 als falsch. x = x + true; // entspricht: x = x + 1; Variablen Variablen müssen vor ihrer Verwendung definiert werden. In C-Programmen erfolgt die Definition traditionell am Anfang der Funktion oder des Blocks, in der sie verwendet werden, in C++/Java meistens kurz vor oder bei ihrer Verwendung. Die Definition geschieht durch Angabe des Typs und des Variablennamens. Es können auch mehrere Variable desselben Typs gemeinsam definiert werden: int x; long i, k, Summe; short s1 = 5, s2 = 3, s3; // 3 long-variable werden definiert // mit oder ohne Initialisierung Eine Zuweisung in einer Definition nennt man Initialisierung. Es handelt sich dabei streng genommen um keine Zuweisung sondern eben um eine Initialisierung. Dabei ist oft mehr

erlaubt, als bei einer echten Zuweisung möglich wäre. Das ist umso wichtiger in C++, weil hier im Rahmen einer Initialisierung auch ein Funktionsaufruf (Konstruktor) erfolgen kann/muss. Der Datentyp auto Neu und mit Freude aufgenommen wurde der neue Typbezeichner auto (seit C++11), bei dem C++ den Typ automatisch aus dem Initialisierer zu erraten versucht. Das geht natürlich nur, wenn die Objekte tatsächlich initialisiert werden (= gleich bei der Definition einen Wert erhalten): auto i = 1; // i ist int auto x = 2.0f; // x ist float auto s = sin(1.90); // s ist double auto u; // das ist ein Blödsinn, wie soll C++ den Typ erraten? std::vector<double> v; std::vector<double>::const_reverse_iterator it = v.crbegin; auto it = v.crbegin(); // C++11: Gott sei Dank gibts auto Konstante Der Typ von Konstanten wie z.b. Zahlenwerte, C-Strings wird an der Form der Konstanten erkannt: 1, 2, -1000: besitzen keinen Dezimalpunkt -> Ganzzahltyp -> int 2.0, 3.14159, 1e5: besitzen einen Dezimalpunkt und/oder Exponent-> double 100'000'000 : 100 Millionen als int (seit C++11 erlaubte Strukturierung langer Zahlen), 1'000'000.000'3 als double Ist man mit dieser Zuordnung nicht zufrieden, kann man noch durch einen/mehrere angehängte/n Buchstaben (u oder U für unsigned, l (schlecht, weil ähnlich zu 1) oder L für long, ll oder besser LL für long long, f oder F für float) der Konstanten einen anderen Typ geben: 1L -> 1 vom Typ long (bitte nicht 1l verwenden, das verwechselt man gerne mit 11) 1uL -> 1 vom Typ unsigned long 1.0f -> 1.0 vom Typ float 1e6 -> eine Million als double

10e6f -> zehn Millionen als float Wenn man short oder unsigned short Konstante spezifizieren will (das ist eigentlich nie wirklich nötig), muss man eine Typ-Umwandlung verwenden. Diese hat in C++ die Form: static_cast<zieltyp>(ausdruck) static_cast<short>(23) Alternativ kann man auch einen Konstruktor verwenden(ist kürzer): short{23} // ab C++11 in C schreibt man dafür (das geht auch in C++, es wird allerdings nicht gerne gesehen) (Zieltyp) Ausdruck (unsigned short) 23 Ganze Zahlen kann man statt dezimal auch im Oktalsystem angeben (diese beginnt dann mit einer 0 (Null!)) oder das Sedezimalsystem (Hexadezimal-System) verwenden, wobei man dann mit 0x beginnen muss: 10 -> 10 010 (Oktalsystem) -> 8 0x10 (Hexen-Ein Mal Eins) -> 16 Seit C++11 ist auch die Angabe im Binärsystem möglich, bei der natürlich nur die Ziffern 0 und 1 erlaubt sind. Sie beginnen mit 0b: 0b11101(statt 0b ist auch 0B möglich) -> 29 dezimal Zeichen-Konstante: Stehen in einfachen Anführungszeichen: 'a' Ascii-Wert des Zeichens a: In C ist das ein int, in C++ ein char, in Java ein char (das ist in Java kein numerischer Typ) '\t' ist das Tabulator-Zeichen, '\n' ist das Newline-Zeichen C-String-Literale oder Zeichenketten-Konstante werden in allen unseren Sprachen in doppelte Anführungszeichen gesetzt: "Ich bin ein String-Literal" In C (und damit auch in C++) und Java handelt es sich dabei um ein Array von char, das sind Zeichen, die im Speicher hintereinander liegen: also ein I, ein c, ein h, ein Leerzeichen usw. bis zum l von Literal und danach ein Null-Byte, das den String terminiert. Die Länge des Strings wird nicht abgespeichert, er geht eben bis zum ersten Nullbyte. Wer dynamisch Zeichenketten erzeugt und auf das schließende Nullbyte vergisst, hat u.u. sehr lange Strings generiert!