Post on 10-Jun-2018
Virtuelle
Produktentwicklung
Einführung in die Programmiersprache C
P r o f . D r . - I n g . F r a n k L o b e c k
2 2014 © Universität Duisburg-Essen
Einleitung
3 2014 © Universität Duisburg-Essen
Ein le i tung
Computerprogramme sind so genannte „ausführbare Dateien“. Unter Windows können Programme durch
Doppelklicken ausgeführt werden.
Ein Computerprogramm muss in einer für den Computer verständlichen Sprache (genauer gesagt für das
Betriebssystem) vorliegen, damit es ausgeführt werden kann. Da der binäre Programmcode für Menschen schwer
lesbar ist, werden Programmiersprachen verwendet.
Aus dem Code einer Programmiersprache wird ein für den Computer verständlicher Code generiert:
Src-Datei
„Test.c“
Header-Datei
„Test.h“
Präprozessor
Header-Datei
„stdio.h“
Textueller Ersatz
Compiler
Objekt-Datei
„Test.obj“
Syntaxprüfung
Übersetzung in
Binärformat
Linker
Bibliotheks-Datei
„stdlib.lib“
Programm-Datei
„Test.exe“
Binden der
Objektdateien
4 2014 © Universität Duisburg-Essen
Entwicklungsumgebung
5 2014 © Universität Duisburg-Essen
Visua l S tud io
Die Entwicklungsumgebung Visual Studio ermöglicht die komplette Entwicklung und Test von C-Programmen.
Der erste Schritt zur Erstellung eines Programms ist das Erzeugen eines neuen Projektes.
Damit ein lauffähiges C-Projekt erstellt wird, müssen die nachfolgend beschriebenen Schritte ausgeführt werden.
1. Datei – Neu - Projekt
6 2014 © Universität Duisburg-Essen
Visua l S tud io
2. Win32-Konsolenanwendung auswählen
3. Projektnamen eingeben
4. Verzeichnis auswählen
5. OK wählen
6. Unter „Anwendungseinstellungen“: Leeres Projekt wählen
7 2014 © Universität Duisburg-Essen
Visua l S tud io
7. Eine Datei dem Projekt hinzufügen.
• In der Projektmappe Quelldateien auswählen
• Rechte MT – Hinzufügen – Neues Element
8 2014 © Universität Duisburg-Essen
Visua l S tud io
8. Eine neue Datei erstellen.
Diese Datei als C-Datei speichern.
9 2014 © Universität Duisburg-Essen
Visua l S tud io
9. Nun steht ein neues leeres Projekt zur Verfügung. Im nächsten Schritt kann der Programm-Code in die C-Quelltext-
Datei eingegeben werden.
Der Quelltext wird mit Hilfe des Befehls: Erstellen - <Projektname> erstellen in ein ausführbares Programm übersetzt.
Das erste C-Programm:
10 2014 © Universität Duisburg-Essen
C-Grundlagen
11 2014 © Universität Duisburg-Essen
Grunde lemente von S t ruk togrammen
V Verarbeitung
Bedingte Verarbeitung
(z.B. if ... else ...)
Bedingung W F
V1 V2
Bedingung
Bedingung
abweisende Schleife
nichtabweisende
Schleife
Initialisierung
Verarbeitung
Schrittsteuerung
Bedingung
Zählschleife
Verarbeitung
Verarbeitung
12 2014 © Universität Duisburg-Essen
Al lgeme ines
Problem: Quadratwurzel ziehen Auflisten der Teilprobleme
TP01 = Zahl einlesen
TP02 = Zahl überprüfen
TP03 = Zahl negativ > Hinweis: keine Lösung
TP04 = Zahl positiv > Wurzel ziehen
TP05 = Ergebnis ausgeben
TP06 = Vorgang wiederholen?
TP07 = Ist der eingegebene Wert eine Zahl?
Eine Programmiersprache verarbeitet definierte Sprachelemente,
deren Verwendung und Kombination einer bestimmten Syntax-Regel
unterliegen.
Sprachelemente sind unter anderem:
Variablen, Konstanten, Ausdrücke
Wertzuweisungen
Lese- und Schreib-Anweisungen
Verzweigungen, Schleifen
Funktionen
Zur Strukturierung werden so genannte
Steuerzeichen wie ( ) { } [ ] % , : usw. verwendet.
/* Dies ist der Code Quadratwurzel ziehen */
#include <stdio.h>
#include <math.h>
void main ( )
{
float zahl, wurzel ;
int i ;
char buchstabe ;
do
{
printf („Gib Zahl ein:“) ;
i = scanf („%f, &zahl ) ;
if ( i != 1)
{
printf („Dies ist keine Zahl!“) ;
}
else if ( zahl < 0 )
{
printf („Wurzelwert ist imaginär“) ;
}
else
{
wurzel = sqrt ( zahl ) ;
printf („Wurzelwert = %f“, wurzel ) ;
}
printf ( „Wurzelziehen fortsetzen = j“) ;
scanf ( „%c“, &buchstabe ) ;
}
while ( buchstabe == „j“ ) ;
return ;
}
13 2014 © Universität Duisburg-Essen
Beze ichner , Da ten typen , Ausdrücke , Anw e isungen
Richtige Beispiele für Bezeichner:
breite, _ab, hoehe, x_koordinate, y1, fb12_prof_anz
Falsche Beispiele:
1x, x-wert, höhe, a&b
Hinweis: Es wird zwischen Groß- und
Kleinschreibung unterschie-den, d.h.,
a1 nicht gleich A1
Alle Variablen, Konstanten, Funktionsnamen, etc. werden allgemein Bezeichner genannt. Bezeichner erhalten als 1. Zeichen immer
einen Buchstaben oder das Sonderzeichen _ (underline). Alle folgenden Zeichen können Buchstaben, Ziffern oder das Zeichen
underline sein, deren Kombination frei wählbar ist. Grundsätzlich sollte der gesamte Quellcode mit Kleinbuchstaben ohne Umlaute
geschrieben werden. Einzige Einschränkung sind die Konstanten, diese werden zur besseren Unterscheidung groß geschrieben. Werte
von Variablen können jederzeit geändert werden, Konstanten wie z.B. PI = 3.141592 nicht.
Bezeichner können verschiedene Werte unterschiedlicher Art annehmen. Diese Unterschiede müssen vorab definiert werden. Dies
geschieht mit Hilfe der sogenannten datentyp-Anweisung. Hierbei wird im Wesentlichen zwischen Werten mit oder ohne
Nachkommastellen und Texten unterschieden. Als Datentypen sind erlaubt:
Datentyp
float
double
int
short
long
char
void
Art des Wertes
Gleitkommawert
Gleitkommawert
Festkommawert
Festkommawert
Festkommawert
Textzeichen
Ohne Wert
Wertebereich:
von -3.4 * 1038 bis 3.4 * 1038
von -1.7 * 10308 bis 1.7 * 10308
von -32.768 bis 32.768
von -32.768 bis 32.768
von -2.14 * 109 bis 2.14 * 109
von 0 bis 255 (ASCII-Zeichen)
Definition:
float breite, hoehe ;
double x, y, z ;
int i, k , j ;
short zahl ;
long ziffer ;
char zeichen, text [ ] ;
[ ] wird später erklärt.
Operatoren
= Zuweisung
+ Addition
- Subtraktion
* Multiplikation
/ Division
++ Inkrement
-- Dekrement
14 2014 © Universität Duisburg-Essen
Beze ichner , Da ten typen , Ausdrücke , Anw e isungen
Ein Ausdruck ist eine Folge von Operatoren ( + * - / etc. ) und Operanden ( z. B. Bezeichner ), welche einen Wert
berechnen und/oder ein Objekt bezeichnen und/oder den Typ eines Objektes festlegen oder ändern. Jeder Operand ist selbst
ein Ausdruck. Im einfachsten Fall ist ein Ausdruck nur eine Konstante, Variable oder Funktionsaufruf. Durch die Operatoren
werden Operanden zu komplexeren Ausdrücken, z.B.: x + 17.3 * y In „C“ liefert jeder Ausdruck einen Typ ( datentyp )
und einen Wert. Ausdrücke mit den in der Mathematik üblichen Operatoren werden von links nach rechts unter
Berücksichtigung der bekannten Rechenregeln (z.B. Punktrechnung geht vor Strichrechnung) berechnet. Operatoren, bei
denen von rechts nach links gerechnet wird, werden in diesem Kurs nicht behandelt. Zunächst werden nur arithmetische
Ausdrücke wie a + b behandelt. Zu einem späteren Zeitpunkt folgen noch logische Ausdrücke wie a > b.
Jedes C-Programm besteht aus einer Folge von Anweisungen, die sequentiell abgearbeitet werden. Anweisungen werden
durch ein Semikolon abgeschlossen. So wird jeder Ausdruck durch Anhängen eines Semikolons zu einer Anweisung. Die
einfachste Anweisung ist die leere Anweisung, sie besteht nur aus einem Semikolon. In einer Dateizeile können mehrere
Anweisungen stehen. Die Variablen erhalten ihren Wert in einer Zuweisungs-Anweisung mit Hilfe des Zuweisungsoperators
„=“ :
< variable > = < ausdruck > ;
Links vom Gleichheitszeichen steht eine Variable, deren Wert berechnet werden soll. Der Ausdruck kann eine Konstante,
Variable, ein arithmetischer Ausdruck, ein logischer Ausdruck, ein Funktionsaufruf oder eine Kombination aus allen diesen
Elementen sein. Nachfolgend einige Beispiele
c = a + b ;
i = m ;
h = funktion ( a ) ;
a = 3. ;
z = 2. * funktion ( ) / ( a * b ) ;
funktion (x ) ;
a + b = c ;
2 = c ;
funktion ( ) = z ;
Die Beispiele in dieser Reihe sind syntaktisch falsch!
In einer datentyp-Anweisung können mehrere Variablen gleichen Datentyps in einer Liste, durch Komma getrennt,
zusammengefaßt werden. Gleichzeitig können den Variablen in einer datentyp-Anweisung Werte zugewiesen werden, z.B.,
float x = 3. , y = 12. , z ; . Alle anderen Variablen ( hier z ) erhalten den Wert 0
15 2014 © Universität Duisburg-Essen
R e c h e n g e n a u i g k e i t , m a t h e m a t i s c h e F u n k t i o n e n u n d K o n s t a n t e n
Gegeben:
float a, b, c, d ;
int k, i, j, m ;
a = 4. ; k = 4 ;
b = 5. ; i = 5 ;
c = 6. ; j = 6 ;
Aufgabe 1:
d = b / a ;
d = i / k ;
d = i / a ;
m = a / b ;
m = b / a ;
Ergebnisse:
d = ___
d = ___
d = ___
m = ___
m = ___
Aufgabe 2:
____________
______
___ ___
d = k / i + a * b / j ;
Berechnen:
___________
______
___ ___
d = k / i + a * b / j ;
Ergebnis:
d = _____
Für die Berechnung von arithmetischen Ausdrücken gelten die üblichen Regeln der Mathematik (Punktrechnung geht vor
Strichrechnung). Die Berechnung erfolgt in der Regel von links nach rechts und bei Klammern von innen nach außen. Der
Ausdruck rechts vom =-Zeichen wird unabhängig vom Datentyp links vom Gleichheitszeichen berechnet und dann
entsprechend dem Datentyp der Variablen zugewiesen und gegebenenfalls konvergiert. Aus diesem Grunde ist auch die
folgende Anweisung erlaubt:
k = k + 1 ;
Zu beachten ist, dass bei jeder einzelnen Rechenoperation die jeweils beteiligten Datentypen zu berücksichtigen sind.
Allgemein kann man sagen, ist an einer einzelnen Rechenoperation ein Gleitkommawert beteiligt, ist das Zwischenergebnis
vom Typ Gleitkomma. Die folgenden Beispiele sollen dies verdeutlichen:
Berechnen Sie die folgende Aufgabe m = k * i / j ; a) von links nach rechts m = ______
b) von rechts nach links m = ______ (falsch)
Hinweis: Eine Konstante ohne Dezimalpunkt ist vom Typ int (Festkomma), mit
vom Typ double (Gleitkomma).
Lösen Sie nun die beiden Aufgaben, unter der Berücksichtigung, daß x, a, b
vom Typ float sind.
x = 10 / 3 ; x = ________
x = 10. / 3 : x = ________
x = 15. / 3. ; x = ________
a = 8. / 3. ; b = 7. / 3. ; x = a + b ; x = _______
16 2014 © Universität Duisburg-Essen
R e c h e n g e n a u i g k e i t , m a t h e m a t i s c h e F u n k t i o n e n u n d K o n s t a n t e n
Häufig benötigen Sie für die Berechnung mathematische Funktionen, wie z.B., die Quadratwurzel oder die trigonometrischen Funktionen wie sin, cos, etc..
Die Leistungen dieser Funktionen stehen in einer so genannten Header-Datei (include-Datei), die durch die folgende Präprozessoranweisung
bereitgestellt werden:
#include < math.h >
Diese Anweisung muss am Anfang einer Quellcode-Datei stehen. Hier einige mathematischen C-Funktionen:
sqrt ( double ) => Quadratwurzel ziehen
sin (double ) => sinus-Wert aus Bogenmaß
abs ( int ) => Absolutwert berechnen
fabs ( double ) => Absolutwert berechnen
Beispiel: In einem Buchhaltungsprogramm wird an sehr vielen Stellen die Mehrwertsteuer berücksichtigt. Es ist bekannt, dass
sich der Wert der MwSt in den letzten Jahren mehrmals geändert hat. Um dies in dem Programm zu berücksichtigen, müssten
an all diesen Stellen der Wert des Mehrwertsteuersatzes manuell geändert werden. Dabei kann man natürlich sehr leicht eine
Änderung vergessen und damit Fehler in das Programm einbringen. In solchen Fällen werden so genannte symbolische
Konstanten verwendet. Diese Text-Konstanten werden mit Hilfe der folgenden Präprozessoranweisung formuliert:
#define MWST 19
Der Präprozessor ersetzt in dem Quellcode vor der Übersetzung alle Zeichen <MWST> durch die Zeichen <19>.
(Dieser Vorgang heißt auch Textersetzung). Die #define-Anweisung muß vor der ersten Benutzung der Text-Konstanten
(möglichst am Anfang des Quellcodes) stehen. Die Konstanten müssen groß geschrieben werden.
17 2014 © Universität Duisburg-Essen
K o m m e n t a r e , S c h l ü s s e l w ö r t e r , B l o c k , Z u s a m m e n f a s s u n g
/* beliebiger Kommentar */ Zu beachten sind hier jeweils immer nur die Anfangs- ( /* ) und die End-
Markierungen ( */ ).
/*
Dieser Kommentar hat
vier Zeilen
*/
C-Programme können formatfrei geschrieben werden. Zwischenräume (Leerzeichen) spielen keine Rolle.
Jeder Anwender sollte dennoch genügend Gebrauch davon machen (vgl. 01/01), damit das Programm leichter lesbar ist. Des
weiteren ist die Benutzung von Kommentarzeilen sehr sinnvoll, damit jeder zu einem späteren Zeitpunkt noch weiß, warum
der Algorithmus in dieser Form realisiert worden ist. Ein Kommentar kann über mehrere Zeilen gehen und sieht so aus:
In „C“ haben einige Wörter eine ganz bestimmte Bedeutung. Diese Wörter werden auch Schlüsselwörter genannt und
dürfen von dem Programmierer nicht anderweitig verwendet werden. Die Schlüsselwörter sind:
auto
double
if
static
break
else
int
struct
case
entry
long
switch
char
extern
register
typedef
continue
float
return
union
default
for
short
unsigned
do
goto
sizeof
while
Mehrere Anweisungen können durch eine je eine vor- und hinten-angestellte { } zu einem sogenannten Block
zusammengefaßt werden. Dieser Block wird dann von einer übergeordneten Anweisung wie eine Anweisung aufgefaßt.
(Vergleiche auch Programmauszug unten).
18 2014 © Universität Duisburg-Essen
K o m m e n t a r e , S c h l ü s s e l w ö r t e r , B l o c k , Z u s a m m e n f a s s u n g
Mittels eines Programm-Auszuges sollen hier die bis jetzt bekannten Syntax-Regeln zusammengefaßt werden:
Programmauszug
#include < math.h >
{
float a = 2. , j = 3. , c , wurzel ;
c = ( i * j ) / 2. ;
/* Berechnung einer Wurzel aus einem
geometrischen Mittelwert */
wurzel = sqrt ( c ) ;
}
Erläuterung
Bereitstellung der mathematischen Funktionen
{ => Beginn eines Blockes
float => datentyp-Bezeichnung, jeder Bezeichner
muß einen Datentyp erhalten
, => Trennzeichen zwischen gleichartigen Dingen
. => Verwendung immer nur als Dezimalpunkt
; => Ende einer Anweisung
= => Ergibt-Anweisung, Berechnung von links
nach rechts nach üblichen Rechenregeln
/* => Beginn einer Kommentarzeile
*/ => Ende einer Kommentarzeile
sqrt => Aufruf einer mathematischen Funktion
} => Ende eines Blockes
Übung: Formulieren Sie nun einen Programmauszug, der jeweils das Verhältnis der Flächen und der Umfänge von einem
Kreis zu einem Quadrat berechnet. Der Durchmesser des Kreises entspricht der Diagonale des Quadrates. Der
Programmauszug soll auch alle datentyp-Anweisungen enthalten
19 2014 © Universität Duisburg-Essen
C-E lement : Funk t ion
In „C“ werden die einzelnen Lösungsalgorithmen in Form von Funktionen formuliert, die bestimmte Aufgaben ausführen.
Jede Funktion erhält einen Funktions-Namen. Dann folgt der Funktionsrumpf als Folge von Anweisungen in Form eines
Blockes. Das Ende der Funktion wird durch eine return-Anweisung angezeigt. Eine Funktion kann Eingabewerte und
Ausgabe- oder Rückgabewerte besitzen. Auch das Hauptprogramm ist in „C“ eine Funktion und muß den Namen main
erhalten. Ohne eine Funktion main gibt es kein ausführbares Programm. Die Syntax einer Funktion in der allgemeinen Form
lautet:
Syntax: < datentyp > < funktionsname > ( < argumentliste > )
{
< Folge von Anweisungen ; >
return ( < rückgabewert > ) ;
}
Beispiel 1
void main ( )
{
int a = 2 , b = 6 , c ;
c = a / b ;
return ;
}
Funktionen sind in sich abgeschlossen und alle in der Funktion definierten Variablen sind auch nur innerhalb der Funktion
gültig. Funktionen können beliebig oft von anderen Funktionen aufgerufen werden. Eine Funktion kann über die Argumentliste
mehrere Eingangswerte erhalten, aber nur einen Wert (rückgabewert) über den Funktionsnamen an die rufende Funktion
zurückgeben (s. Beispiel 2). Die argumentliste ( .. ) muß immer angeführt werden, auch wenn keine Eingangsparameter
benötigt werden. Funktionen mit dem datentyp void, haben keinen rückgabewert und damit auch keine ( .. ) hinter der
return-Anweisung. Wie trotzdem Variablen verändert werden können, die sowohl innerhalb als auch außerhalb des
Gültigkeitsbereichs der Funktion vorkommen, wird zu einem späteren Zeitpunkt in dem Kapitel „pointer“ (08/01) vorgestellt.
20 2014 © Universität Duisburg-Essen
C-E lement : Funk t ion
Funktionen ermöglichen es, Programme in kleinere, mehr oder weniger selbständige Einheiten zu zerlegen und so die
Übersichtlichkeit und Wartbarkeit der Programme zu erhöhen. Prinzipiell müssen alle in einem Programm benutzten
Funktionen dem Compiler bekannt sein. Zunächst wird die Funktion mittel_wert definiert und dann von main aufgerufen. (s.
Beispiel 2)
Besser und übersichtlicher ist es, die jeweils benutzte Funktion vorab nur zu deklarieren (s. Beispiel 3) und die eigentliche
Definition der Funktion zu einem späteren Zeitpunkt zu platzieren.
Die Variablen m, i, k gelten nur in der Funktion mittel_wert. Die Variable c gilt nur in der Funktion main. Der Wert der
Variablen m wird über den Funktionsnamen mittel_wert an die Funktion main zurückgegeben und der Variablen c
zugewiesen.
Beispiel 2 /* Definition der Funktion */
int mittel_wert ( int k , int i )
{
int m ;
m = (k + i ) / 2 ;
return ( m ) ;
}
/* Hauptprogramm */
void main ( )
{
int c ;
c = mittel_wert ( 2 , 3 ) ;
return ;
}
Welchen Wert erhält c = ___
Beispiel 3 /* Deklaration der Funktion */
int mittel_wert ( int , int ) ;
/* Hauptprogramm */
void main ( )
{
int c ;
c = mittel ( 2 , 3 ) ;
return ;
}
/* Definition der Funktion */
int mittel_wert ( int k , int i )
{
int m ;
m = (k + i ) / 2 ;
return ( m ) ;
}
21 2014 © Universität Duisburg-Essen
C-E lement : Funk t ion
Funktionen, die in verschiedenen Programmen benötigt werden, stehen in separaten Quell-Dateien < name.c >. Die
Deklarationen werden dann in so genannten Header-Dateien < name.h > zusammengefaßt und mit einer #include-
Anweisung eingelesen. Auf diese Art und Weise lassen sich die Funktionen leichter verwalten und ändern.
#include „mittel_wert.h“
void main ( )
{
< Anweisungen >
/* Aufruf von mittel_wert */
j = mittel_wert ( 5, 7 );
}
Datei: mittel_wert.h int mittel_wert ( int , int ) ;
Datei: mittel_wert.c
Gesamte Definition der Funktion mittel_wert
int mittel_wert ( int k , int i )
{
int m ;
m = (k + i ) / 2 ;
return ( m ) ;
}
22 2014 © Universität Duisburg-Essen
C-E lement : Funk t ion
Im Zusammenhang mit der Benutzung von Funktionen soll hier auf den Unterschied von lokalen und globalen Variablen
eingegangen werden. Die Variable x4 ist global, da sie außerhalb der Funktion deklariert wurde. Der Inhalt von x4 kann
jederzeit verändert werden.
Die Variablen x1, x2 und x3 sind lokal. Die Variablen x1 und x2 in den Funktionen main und mult sind völlig verschiedene
Variablen. Ihr Gültigkeitsbereich beschränkt sich auf die jeweiligen Funktionen und deshalb sind ihre Werte auch nicht
übertragbar. Dies bedeutet, die Variablen x1 und x2 sind nur Eingangs-werte für die Funktion mult. Ihre Veränderungen
innerhalb der Funktion mult sind für die Werte von x1 und x2 in der Funktion main ohne Bedeutung.
Der Rückgabewert kann auch ein ausdruck sein. Der datentyp des Rückgabewertes ( hier x1 ) muß mit dem datentyp der
Funktion ( hier mult ) übereinstimmen.
float mult ( float, float ) ;
float x4 = -3. ;
void main ( )
{
float x1, x2, x3 ;
x1 = 5 ;
x2 = 2 ;
x3 = mult ( x1, x2 ) * x4 ;
/* Wie groß sind hier x1, x2, x3, x4 ?*/
}
float mult ( float x1, float x2 )
{
x4 = 12. ;
x1 = x1 * x2 ;
return x1 ;
}
x1 = x2 = x3 = x4 =
23 2014 © Universität Duisburg-Essen
C-E lement : Funk t ion
Schreiben Sie nun gemäß unten stehender Skizze eine Funktion zur Berechnung der Spannung eines eingespannten
Biegebalkens, der mit einer senkrechten Kraft am Ende (bei der Länge l ) des Balkens belastet wird. Der Querschnitt
ist ein Rechteck mit den Abmessungen b und h.
Mathematische Grundlagen:
Moment = Kraft * Länge
Spannung = Moment / Widerstandsmoment
Widerstandsmoment = Breite * Höhe2 / 6
Da die Lese- und Schreibanweisungen in „C“ noch nicht bekannt sind, benutzen Sie bitte folgende Anwender-Funktionen
zum Lesen und Schreiben von double-Werten:
Lesen Sie die Werte für Kraft und Länge einzeln mit der Funktion < eingabe ( „beliebiger Text“) ; > ein, wobei der
Bezeichner eingabe die jeweils von Ihnen eingegebenen Werte zurückliefert.
Die Ausgabe der Spannung realisieren Sie mit der Funktion < ausgabe („Text“, < wert > , „Text“) ; >.
Beide Funktionen sind vom Typ double und die Deklarationen stehen in der Header-Datei < einaus.h >.
Hinweis: Bevor Sie beginnen, sollten Sie die Dateien < einaus.h > und < einaus.c > in Ihr Heimatverzeichnis kopieren.
Beide Dateien stehen auf dem BSCW-Server zum Download zur Verfügung.
B L
F
H
Skizze:
24 2014 © Universität Duisburg-Essen
C-E lemente : scan f und p r in t f
In der Regel benötigt jedes Programm zur Berechnung die Eingabe von Werten und die Ausgabe der berechneten Ergebnisse.
Die in dem Übungsbeispiel „Biegebalken“ benutzten Funktionen eingabe und ausgabe sind Anwender-Funktionen, welche die
Standard-Eingabe-Funktion ( scanf ) und die Standard-Ausgabe-Funktion ( printf ) von „C“ beinhalten. (Standard: Eingabe
von der Tastatur, Ausgabe auf den Bildschirm.)
Die Eingabe eines Variablenwertes in „C“ geschieht mit der Funktion scanf. Die Syntax lautet:
scanf ( „ < formatparameter > “ , < &variable > ) ;
Der Formatparameter (eine Kombiantion aus %-Zeichen und Buchstaben) gibt an, welchen Datentyp die einzulesende Variable
erhalten soll. Sollen mit einer scanf-Anweisung mehrere Variablen eingelesen werden, müssen entsprechend viele
Formatparameter in Anzahl, Form und Reihenfolge mit der Variablen-Liste übereinstimmen. Das Zeichen & muss vor jedem
Variablennamen in der scanf-Anweisung angegeben werden. In den folgenden Anweisungen ist dieses Zeichen wieder
wegzulassen. Die Erläuterung für diese Vorgehensweise erfolgt später in dem Kapitel „pointer“ bzw. „zeiger“.
„C“ benutzt zum Einlesen des Variablenwertes einen Hilfspuffer mit dem Namen < stdin >. Da der Inhalt dieses Puffers nicht
automatisch gelöscht wird, sollte nach jeder Benutzung von scanf der Inhalt der Datei mit dem folgenden Befehl gelöscht
werden:
fflush ( stdin ) ;
Alle Ausgaben auf den Bildschirm, gleichgültig ob Sie a) einen Text, b) eine Variable oder c) eine Kombination von Text und
Variable ausgeben wollen, werden mit der printf-Anweisung ausgeführt. Statt einer Variablen kann auch ein ausdruck (s.
02/01) eingesetzt werden. Hierbei ist zu beachten, daß der Datentyp des ausdruck- Ergebnis dem Datentyp des
Formatparameter entspricht. Hinweis: Formatparameter = fp genannt.
25 2014 © Universität Duisburg-Essen
C-E lemente : scan f und p r in t f
Syntax:
a) printf ( „<beliebiger Text >“ ) ;
b) printf ( „ < fp > “ , < variable > ) ;
c) printf ( „ text < fp > text “ , < variable > ) ;
fp
%d
%hd
%ld
%f
%lf
%c
%s
Datentyp
int
short
long
float
double
char (1 Zeichen)
char (Zeichenkette)
Alle Ausgaben auf den Bildschirm, gleichgültig ob Sie a) einen Text, b) eine Variable oder c) eine Kombination von Text und
Variable ausgeben wollen, werden mit der printf-Anweisung ausgeführt. Statt einer Variablen kann auch ein ausdruck (s.
02/01) eingesetzt werden. Hierbei ist zu beachten, daß der Datentyp des ausdruck- Ergebnis dem Datentyp des
Formatparameter entspricht. Hinweis: Formatparameter = fp genannt.
Auch für die printf-Anweisung gilt, daß die auszugebenden Variablen in Anzahl, Form und Reihenfolge mit den
Formatparametern übereinstimmen müssen. Zur besseren Strukturierung der Ausgabe kann die Formatangabe durch weitere
sogenannte Format-Zeichen ergänzt werden, z.B.:
\n => neue Zeile an dieser Position
%-d => ein Minuszeichen vor dem Buchstaben gestattet eine linksbündige Ausgabe, sonst rechtsbündig
%3f => die Ziffer gibt die maximale Anzahl der Stellen für die Ausgabe an
%6.2lf => maximale Anzahl von 6 Stellen inklusive 2 Nachkommastellen für die Ausgabe.
Beispiel:
int anzahl = 4 ; float flaeche = 17.2 ;
printf ( “Dies ist ein Test“ ) ;
printf ( “%-6d“, anzahl ) ;
printf ( “Fläche = %8.2lf qmm“, flaeche ) ;
|_|_|_|_|_|_|_|_|_|_|_|_|_|_|_|_|_|_|_|_|_|_|_|_|_|
|_|_|_|_|_|_|_|_|_|_|_|_|_|_|_|_|_|_|_|_|_|_|_|_|_|
|_|_|_|_|_|_|_|_|_|_|_|_|_|_|_|_|_|_|_|_|_|_|_|_|_|
Aufgabe: Lesen Sie zwei ganze Zahlen ein und lassen den Mittelwert
berechnen und ausgeben.
int z1, z2, zs ;
scanf ( “%d %d“ , &z1, &z2 ) ;
fflush ( stdin ) ;
zs = ( z1 + z2 ) / 2 ;
printf ( “Mittelwert = %8d\n “ , zs ) ;
26 2014 © Universität Duisburg-Essen
C-E lemente : scan f und p r in t f
Formulieren Sie nun die Variablendefinitionen und eine printf-Anweisung für die folgende Ausgabe
|_|_| 5 Schrauben M 10 * 30.0 vernickelt.
Übung: Ersetzen Sie nun in Ihrer Übungsaufgabe „Biegebalken“ die Anwender-Funktionen eingabe und ausgabe durch
entsprechende scanf- und printf-Anweisungen.
Hinweis: Innerhalb der beiden „ “ – Zeichen ist in der printf-Anweisung der gesamte Zeichenvorrat erlaubt, also auch
Umlaute. Des weiteren werden hier auch alle Leerzeichen bei der Ausgabe berücksichtigt. Vor jeder scanf-Anweisung sollte
eine printf-Anweisung dem Benutzer mitteilen, was eingelesen werden soll. Die Leistungen der scanf- und printf-Anweisung
erhalten Sie durch die Anweisung #include < stdio.h > vor der Anweisung void main. Falls Sie später mehrere
Quellcode-Dateien haben, muß in jeder Datei diese #include – Anweisung stehen, in der Sie eine scanf- oder printf-
Anweisung formuliert haben.
Hinweise bei der Benutzung der scanf-Funktion.
int i , j ;
scanf („%d %d“, &i , &j ) ;
Hinweis: Wenn Sie vor dem 2. „-Zeichen ein Blank einfügen, müssen Sie ein zusätzliches
Zeichen (s. rechts) eingeben.
Blanks zwischen den Formatparametern sind ohne Bedeutung.
Eingabe 1:
| 3 4 (Return-Taste)
Eingabe 2:
| 3 (Return-Taste)
| 4 (Return-Taste)
„%d %d “
^
Blank
| 3 (Return-Taste)
| 4 (Return-Taste)
| a (Return-Taste)
27 2014 © Universität Duisburg-Essen
C-E lemente : scan f und p r in t f
Ein guter Programmierer überprüft, ob die vom Anwender eingegebenen Werte auch syntaktisch richtig sind. Wenn z.B. die
Eingabe einer Zahl gefordert ist, darf der Anwender keinen Buchstabe eingeben. In diesem Fall ist die einzulesende Variable
mit keinem Wert belegt und dies führt in der Regel zu einem Programmfehler bis hin zu einem Programmabbruch. Man kann
dieses leicht überprüfen, da die scanf-Funktion, wie jede andere Funktion einen Rückgabewert ( hier vom Typ int ) besitzt Ein
kleines Beispiel wird dies verdeutlichen.
Bis jetzt nützt diese Kenntnis noch nichts, da Sie noch keine Möglichkeit kennen, wie die fehlerhafte Eingabe programmintern
erkannt und wiederholt werden kann. An späterer Stelle wird noch einmal auf die scanf-Überprüfung eingegangen.
Beispiel:
int i , j , m ;
m = scanf ( „%d %d“, &i , &j ) ;
fflush ( stdin ) ;
Eingabe:
| 3
| 4
m = ____
Eingabe:
| 3
| a
m = ____
Eingabe:
| a
| 4
m = ____
Eine weitere Besonderheit. Wenn eine Zeichenkette mit scanf eingelesen werden soll, darf die Variable kein &-Zeichen
erhalten. Die Begründung dafür erfolgt später im Zusammenhang mit der Behandlung von Pointern.
28 2014 © Universität Duisburg-Essen
Ausw ah lkons t ruk te : Zw e ise i t ige Ausw ah l
Syntax:
if <Bedingung>
{
<Anweisung 1>
}
else
{
<Anweisung 2>
}
zwei Auswahlmöglichkeiten
Zweiseitige
Auswahl
Bedingung=wahr?
ja nein
Anwei-
sungsblock
1
Anwei-
sungsblock
2
Beispiel:
if ( betrag <=0 ) {
printf ( “Der Wert muss groesser Null sein !\n“);
}
else
{ betrag = sqrt( Betrag ); printf (“Die Wurzel ist: %lf \n“, betrag); }
29 2014 © Universität Duisburg-Essen
Ausw ah lkons t ruk te
Das Programm besitzt ...
eine Auswahlmöglichkeit
Einseitige
Auswahl
zwei Auswahlmöglichkeiten mehrere Auswahlmöglichkeiten
Zweiseitige
Auswahl
Mehrstufige
Auswahl
Mehrseitige
Auswahl
(Fallauswahl)
Bedingung=wahr?
ja nein
bleibt
leer Anweisung1
Anweisung1
.......
Bedingung=wahr?
ja nein
Anwei-
sungsblock
1
Anwei-
sungsblock
2
Bedingung=wahr?
Bedingung=wahr?
ja
ja
nein
nein Anwei-
sungs-
block
1
Anwei-
sungs-
block
2
nein ja Bedingung=wahr?
Anweisungs-
block 3
Anweisungs-
block 4
30 2014 © Universität Duisburg-Essen
C-E lement : i f
Es kommt häufig vor, daß die Fortsetzung eines Programmes an eine
Bedingung geknüpft ist. Will man aus einem Wert eine Quadratwurzel
ziehen, so ist dies nur möglich, wenn der Wert >= 0 ist. Bei negativen
Werten ist der Wurzelwert imaginär und somit nicht definiert. Ähnliches
gilt für die Gleichung y = 1. / x , wenn x = 0 ist. Denn dann erhält y den
Wert unendlich und dieser Wert ist nicht definiert. In derartigen Fällen ist
die if-Anweisung anzuwenden. Die Syntax lautet
Programmauszug
double wert, wurzel, x, y ;
wert = -12. ;
wurzel = sqrt ( wert ) ;
x = 0. ;
y = 1. / x ;
Logische Ausdrücke wie z.B. ( a > b ) entstehen durch den Vergleich von 2 oder mehreren Werten miteinander. Der
Ausdruck a > b bedeutet a größer b . Wenn a tatsächlich größer als b ist, so ist der Ausdruck „wahr“ (int-Wert = 1), wenn
nicht ist der Ausdruck „falsch“ (int-Wert = 0). Hierbei können die Vergleichswerte, hier z.B. a und b selbst wiederum
komplexe Ausdrücke sein.
Logische Ausdrücke sind miteinander kombinierbar durch verschiedene UND- oder ODER-Verknüpfungen. Hierbei ist zu
beachten, daß das UND stärker bindet als das ODER und der Gesamtausdruck einer UND-Verknüpfung nur „wahr“ ist, wenn
alle Teilausdrücke „wahr“ sind. Beachten Sie bitte, daß durch Setzen von Klammern die Ausdrücke verändert werden können.
Folgende Vergleichsoperatoren sind unter anderem erlaubt:
if ( < ausdruck > ) < Anweisung ; >
Die Anweisung wird nur ausgeführt, wenn der Ausdruck als logischer Ausdruck „wahr“ ist oder wenn der Ausdruck als
arithmetischer Ausdruck ungleich Null ist.
Arithmetische Ausdrücke wie ( a + b / c ) bedürfen keiner besonderen Erläuterung (vgl. 02/01). Der Ausdruck kann auch nur
jeweils eine Variable, eine Konstante oder ein Funktionsaufruf mit Rückgabewert sein. Beispiel:
Gegeben: float a =2., b = 6., c = -3. , x
=5. ;
if ( a + b / c ) x = 10. ;
x = ____
if ( 5 ) x = 10. ;
x = ____
31 2014 © Universität Duisburg-Essen
C-E lement : i f
Operatoren
a > b
a >= b
a == b
a < b
a <= b
a != b
! a
a && b
a || b
Bedeutung
a größer b
a größer oder gleich b
a identisch mit b
a kleiner b
a kleiner oder gleich b
a ungleich b
ungleich a
a und b
a oder b
Gegeben:
a = 2.; b = 3. ;
c = -2. ; d = 0. ;
g = 6. ;
w oder f ?
if ( a >= b ) ___
if ( g != (c * b ) ) ___
if ( g / b == a ) ___
w oder f ?
if ( d ) ___
if ( b / c ) ___
if ( c * c > b - a ) ___
w oder f ?
if ( a < b || g == d && c <= b )
w oder f ?
if ( a < b || g == d ) && c <= b )
Wenn statt einer Anweisung jeweils mehrere Anweisungen zur Ausführung kommen sollen, so sind
die einzelnen Anweisung durch einen Block (vgl. 02/03) zu ersetzen.. Ein Block wird von der
vorherigen Anweisung immer wie eine einzelne Anweisung aufgefaßt. if ( < ausdruck > )
{
< Anweisung 1 ; >
< Anweisung 2 ; >
}
Gegeben:
x = 0. ; y
= 1. ;
Wenn
a = 0.
Wenn
a = 2.
if ( a > 1)
x = 2 ; y =
3 ;
x = ___
y = ___
x = ___
y = ___
if ( a > 1)
{ x = 2 ; y
= 3 ; }
x = ___
y = ___
x = ___
y = ___
if ( a = 1)
x = 2 ; y =
3 ;
x = ___
y = ___
x = ___
y = ___
32 2014 © Universität Duisburg-Essen
C-E lemente : e lse und e lse i f
if ( < ausdruck > ) < Anweisung 1 ; >
else < Anweisung 2 ; >
Ausdruck gleich
wahr => Anweisung 1
falsch => Anweisung 2
Wenn in Abhängigkeit von dem Ergebnis eines Ausdrucks ( „wahr“ oder „falsch“ bzw. ungleich Null oder gleich Null ) die
Ausführung von 2 alternativen Anweisungen ( Anweisung 1 sonst Anweisung 2 ) gefordert wird, so lautet die Syntax:
Auch hier gilt, wenn mehrere Anweisungen in Abhängigkeit des Ausdruckes zur Ausführung gelangen sollen, ist ein Block
anzuwenden
Syntax:
if ( < ausdruck > )
{
< mehrere Anweisungen ; >
}
else
{
< mehrere Anweisungen ; >
}
Gegeben:
a = 2. ; b = -2. ; d = 0. ;
Wie groß ist:
a = ____ d = _____
Wie groß wäre a und d ,
wenn b = 2. ist?
a = ____ d = _____
Beispiel 1:
if ( b > 0. )
{
a = 7. ;
d = 1. ;
}
else
{
a = 3. ;
d = -4. ;
}
33 2014 © Universität Duisburg-Essen
C-E lemente : e lse und e lse i f
if-Anweisungen lassen sich in vielfältiger Weise verschachteln, solange die Syntax nicht verletzt wird. So kann z.B. jede else-
Anweisung mit einer if-Anweisung kombiniert werden. Man spricht dann von einer else if-Anweisung. Die Syntax lautet
dann:
Übung: Sichern Sie nun in der Aufgabe „Biegebalken“ Ihre Eingaben mittels if-Anweisungen gegen Fehler ab.
Syntax:
if ( < ausdruck 1 > )
{
< Anweisung 1 > ;
}
else if ( < ausdruck 2 > )
{
< Anweisung 2 > ;
}
else
{
< Anweisung 3 > ;
}
/* Fortsetzung des
Programms */
Beispiel 2: d = 0. ;
if ( zahl < 0 )
{
d = 7. ;
}
else if ( zahl == 0 )
{
d = -10. ;
}
else
{
d = -5. ;
}
Ergebnis für d, wenn:
a)
zahl = 7 ,
d = _____
b)
zahl = -2 ,
d = _____
c)
zahl = 0 ,
d = _____
Die Auswertung der beiden Ausdrücke ( ausdruck1 , ausdruck2 ) führt dazu, daß nur eine
der drei Anweisungen ausgeführt wird. Gleichgültig welche Anweisung ausgeführt wird
(vgl. Beispiel 2 ). Die Fortsetzung der Bearbeitung des Programms erfolgt immer an der
gleichen Stelle (s. Syntax links ).
34 2014 © Universität Duisburg-Essen
C-E lemente : sw i tch , case und b reak
Das letzte Beispiel in 04/02 macht deutlich, dass die Anwendung mehrerer verschachtelter if-Anweisungen zu einem recht
unübersichtlichen Programmaufbau führen kann. Wenn der Vergleichsausdruck für eine Verzweigung entweder ein
ganzzahliger Wert ( datentyp int, short oder long ) oder ein Text-Zeichen ( datentyp char ) ist, lassen sich mit Hilfe der
switch-Anweisung in Verbindung mit verschiedenen case-Anweisungen derartige Algorithmen eleganter lösen. Die Syntax
lautet:
Ausdruck vom Typ int
switch ( < ausdruck > )
{
case 1: < Anweisung 1 > ;
< Anweisung 2 > ;
break ;
case 3: case 4: < Anweisung 3 > ;
break ;
default: < Anweisung 4 > ;
}
/* Fortsetzung des Programms */
Ausdruck vom Typ char
switch ( < ausdruck > )
{
case ‘a‘: < Anweisung 1 > ;
< Anweisung 2 > ;
break ;
case ‘c‘: case ‘p‘: < Anweisung 3 > ;
break ;
default: < Anweisung 4 > ;
}
/* Fortsetzung des Programms */
Der Ausdruck in der switch-Anweisung muß entweder vom Datentyp int (oben links) oder vom Datentyp char (oben rechts)
sein. Die switch-Anweisung ermittelt den Wert des Ausdruckes, der als Vergleichswert für die nachfolgenden case-
Anweisungen dient. Bei Übereinstimmung werden die zur case-Anweisung zugehörigen Anweisungen ausgeführt. In den case-
Anweisungen dürfen nur Konstanten oder einzelne Text-Zeichen stehen. Eine Anweisung kann auch für verschiedene case-
Konstanten gelten. Die Konstanten unterliegen keiner Reihenfolge, z.B. nach Größe geordnet.
Die jeweils anschließende break-Anweisung beendet den case-Zweig und verhindert somit die Ausführung der nachfolgenden
Anweisungen. Die Fortsetzung des Programms erfolgt immer nach der }. Fehlt die break-Anweisung werden alle Anweisungen
nach der durch Vergleich gefundenen case-Anweisung bis zur nächsten break-Anweisung ausgeführt. Wird bei keiner der
case-Anweisung eine Übereinstimmung erzielt, werden die Anweisungen der default-Anweisung ausgeführt. Die default-
Anweisung ist nicht zwingend vorgeschrieben, sollte aber in der Regel als Fehlerhilfe von dem Programmierer für den
Anwender genutzt werden.
35 2014 © Universität Duisburg-Essen
C-E lemente : sw i tch , case und b reak
Ein typischer Anwendungsfall für die Kombination der switch-
und case-Anweisungen ist das nach-folgende Beispiel.
Sie möchten das untenstehende Menü ausgeben und in Abhän-
gigkeit einer Ziffer unterschiedliche Programm-Leistungen
realisieren.
Rechts sehen Sie den zugehörigen Programmauszug.
Programmauszug
int ziffer ;
printf ( „ Menü-Übersicht \n ---------------------------“ ) ;
printf ( „ 1 = Werte einlesen \n 2 = Werte berechnen“) ;
printf ( „ 3 = Ausgabe der Ergebnisse \n 4 = Programm beenden
“ ) ;
printf ( „ --------------------------- \n Gib Ziffer: “) ;
scanf ( „%d“, &ziffer ) ;
fflush ( stdin ) ;
switch ( ziffer )
{
case 1: eingabe ( .......) /* Anwender-Funktion */
break ;
case 2: berechne ( ......) /* Anwender-Funktion */
break ;
case 3: ausgabe ( .......)/* Anwender-Funktion */
break ;
case 4: return ;
break ;
default: printf ( „Ziffer %d nicht definiert! \n“ ) ;
}
Menü-Übersicht
---------------------------------
1 = Werte einlesen
2 = Werte berechnen
3 = Ausgabe der Ergebnisse
4 = Programm beenden
---------------------------------
Gib Ziffer:
36 2014 © Universität Duisburg-Essen
Wiederho lungskons t ruk te
Die Zahl der
Wiederholungen ist ...
zahlenmäßig
bekannt
von Bedingungen
abhängig
Bedingte
Wiederholung
Kopfgesteuerte
Wiederholung
Fußgesteuerte
Wiederholung
Zählergesteuerte
Wiederholung
Zählergesteuerte Wiederholung:
for (<initialisierung> ; <bedingung> ; <iteration> )
{
<Anweisungen>
.....
}
Kopfgesteuerte Wiederholung:
while ( <bedingung>)
{
<Anweisungen>
.....
}
Fußgesteuerte Wiederholung:
Do
{
.....
.....
} while ( <bedingung> );
37 2014 © Universität Duisburg-Essen
C-E lemente : w h i le , do und fo r
Sie haben sicherlich auch festgestellt, dass bei einer fehlerhaften Eingabe die erneute Eingabe eines Wertes einen
Rücksprung innerhalb des Programms erfordert. In anderen Programmiersprachen wird hier einfach die goto-Anweisung
benutzt. In „C“ spricht man von einem schlechten Programmierstil, wenn in einer derartigen Situation die goto-Anweisung
benutzt wird. Wiederholungen werden in „C“ immer mit Schleifen ausgeführt. Als Schleifen stehen die Elemente while, do
und for zur Verfügung.
Für alle Schleifen gelten folgende Randbedingungen:
Es wird mindestens eine Schleifenvariable ( hier: < lauf > ) definiert.
Zu Beginn der Schleife liegt ein Anfangswert ( hier: < startwert > ) vor.
Ein Wert für die Änderung ( hier: < schritt > ) der Schleifenvariablen ist bekannt. Der Änderungswert darf auch negativ
sein.
Eine Bedingung ( hier: < abbruchbedingung > ) für die Dauer der Wiederholungen liegt vor. Solange die
Abbruchbedingung „wahr“ oder ungleich 0 ist (vgl. 04/01), wird die Wiederholung fortgesetzt.
Der Wiederholungsbereich wird bei mehr als einer Anweisung durch einen Block ( { .... } ) definiert.
Im Folgenden sehen Sie die Syntax der drei Schleifen im Vergleich:
38 2014 © Universität Duisburg-Essen
C-E lemente : w h i le , do und fo r
Bei allen drei Schleifen wird der Wiederholungsbereich { } solange durchlaufen, wie die Abbruchbedingung „wahr“ oder
„ungleich Null“ ist. Bei Abbruch wird die Bearbeitung an der gekennzeichneten Stelle fortgesetzt. Des weiteren kann man
auch mit Hilfe der break-Anweisung (vgl. 04/03) in Verbindung mit einer if-Anweisung den Wiederholungsbereich ebenfalls
verlassen. Auch hier erfolgt eine Fortsetzung an der Stelle /* Forts..........
Bei der for-Schleife ist die Reihenfolge für die Bearbeitung der Anweisungen in der for-Anweisung zu beachten: a)
Definition Startwert b) Überprüfen der Abbruchbedingung c) Ausführen der Anweisungen d) Veränderung der
Schleifenvariablen e) Überprüfen der Abbruchbedingung f) siehe c) , usw.
Wenn Sie die drei Schleifen vergleichen, werden Sie feststellen, daß die do-Schleife unabhängig vom Startwert und der
Abbruchbedingung immer mindestens einmal durchlaufen wird. Aus diesem Grunde wird diese Schleife auch
nichtabweisende oder fußgesteuerte Schleife genannt. Die beiden anderen Schleifen gehören zu den abweisenden oder
kopfgesteuerten Schleifen. Welche Schleife zum Einsatz kommt, hängt in erster Linie vom Anwendungsfall ab. Es gibt
keine zwingenden Gründe für die Verwendung der einen oder anderen Schleife.
Übung: Ergänzen Sie die Übungsaufgabe „Biegebalken“ so, daß Sie eine falsche Eingabe wiederholen können.
while
lauf = startwert ;
while ( < abbruchbedingung > )
{
< Anweisungen ; >
lauf = lauf + schritt ;
}
/* Fortsetzung des Programms */
do
lauf = startwert ;
do
{
< Anweisungen ; >
lauf = lauf + schritt ;
} while ( < abbruchbedingung > ) ;
/* Fortsetzung des Programms */
for
for ( lauf = startwert ; < abbruchbedingung > ; lauf = lauf + schritt )
{
< Anweisungen ; >
}
/* Fortsetzung des Programms */
39 2014 © Universität Duisburg-Essen
C-Element : „End lossch le i fe“
Berechnen Sie nun den Wert der Variablen < summe > und < i > in den folgenden drei Beispielen:
summe = 0 ;
i = 0 ;
while ( i <= 5 )
{
i = i + 1 ;
summe = summe + i ;
}
summe = ____ i = ___
summe = 0 ;
i = 0 ;
do
{
i = i + 1 ;
summe = summe + i ;
} while ( i <= 5 ) ;
summe = ____ i = ___
summe = 0 ;
for ( i = 0 ; i <= 5 ; i = i + 1 )
{
summe = summe + i ;
}
summe = ____ i = ___
Vorsicht: Bei der Formulierung der Abbruchbedingung ist unbedingt darauf zu achten, daß Sie keine so genannte
Endlosschleife erzeugen. Wenn z.B. trotz Änderung der Schleifenvariablen die Abbruchbedingung immer „wahr“ oder
„ungleich Null“ ist, führt dies zu einer ständigen Wiederholung des Programmabschnittes ohne Unterbrechung. Dies tritt z.B.
ein, wenn im obigen Beispiel der Startwert i = 6 wäre.
Manchmal wird dies durch den Programmierer gewollt. In diesem Fall kann er mit Hilfe der break-Anweisung (vgl. 04/03) einen
gewollten Abbruch erzielen.
40 2014 © Universität Duisburg-Essen
C-Element : „End lossch le i fe“
Endlosschleife ohne Abbruch i = 0 ;
summe = 0 ;
while ( 2 )
{
i = i + 1 ;
summe = summe + i ;
}
Endlosschleife mit Abbruch i = 0 ;
summe = 0 ;
while ( 2 )
{
i = i + 1 ;
summe = summe + i ;
if ( i > 5 ) break ;
}
Beispiel: Endlosschleife
Nun können Sie das Beispiel von 04/03 entsprechend
ergänzen. Die Ergänzung ist zur besseren Unterscheidung fett
dargestellt.
Programmauszug int ziffer ;
while ( 1 )
{
printf ( „ Menü-Übersicht \n ---------------------------“ ) ;
printf ( „ 1 = Werte einlesen \n 2 = Werte berechnen“) ;
printf ( „ 3 = Ausgabe der Ergebnisse \n 4 = Programm beenden“) ;
printf ( „ --------------------------- \n Gib Ziffer: “) ;
scanf ( „%d“, &ziffer ) ;
fflush ( stdin ) ;
switch ( ziffer )
{
case 1: eingabe ( ........
break ;
case 2: berechne ( ............
break ;
case 3: ausgabe ( ............
break ;
case 4: return ;
break ;
default: printf ( „Ziffer %d nicht definiert! \n ) ;
}
}
Menü-Übersicht
--------------------------------
1 = Werte einlesen
2 = Werte berechnen
3 = Ausgabe der Ergebnisse
4 = Programm beenden
--------------------------------
Gib Ziffer:
41 2014 © Universität Duisburg-Essen
C-E lement : Fe lder
Bisher konnte eine Variable immer nur einen Wert annehmen. Nun kommt es aber häufig vor, dass eine Variable gleichzeitig
mehrere Werte haben kann, so z.B. die Variable <lottozahl >, die 6 verschiedene Werte erhält. Gibt man den 6 gespielten
Lottozahlen < zsi > und den 6 gezogenen Lottozahlen < zgi > jeweils 6 verschiedene Variablennamen, müßte man in einem
Programm, welches zur Gewinnermittlung < anzahl > die gespielten mit den gezogenen Lottozahlen vergleichen soll, eine
Vielzahl ähnlicher Anweisungen durchführen, z.B.
int anzahl = 0, zs1, zs2, zs3, zs4, zs5, zs6, zg1, zg2, zg3, zg4, zg5, zg6 ;
< hier werden die gespielten und gezogenen Zahlen definiert >
if (zs1 == zg1 || zs1 == zg2 || zs1 == zg3 || zs1 == zg4 || zs1 == zg5 || zs1 == zg6 ) anzahl = anzahl + 1 ;
if (zs2 == zg1 || zs2 == zg2 || zs2 == zg3 || zs2 == zg4 || zs2 == zg5 || zs2 == zg6 ) anzahl = anzahl + 1 ;
usw. bis
if (zs6 == zg1 || zs6 == zg2 || zs6 == zg3 || zs6 == zg4 || zs6 == zg5 || zs6 == zg6 ) anzahl = anzahl + 1 ;
In diesem Fall bietet es sich an, die Variablen jeweils als Feld ( array ) zu deklarieren.
Ein Feld hat eine bestimmte Anzahl von Variablenwerten mit dem gleichen Variablennamen. Auf die einzelnen Werte wird
über einen sogenannten Index oder eine Adresse zugegriffen. Indizes sind immer ganzzahlig und müssen deshalb vom
Datentyp int sein. Die Länge des Feldes bzw. die Anzahl der Elemente wird mit Hilfe von 2 [ ] angegeben.
Zu beachten ist, dass in „C“ der erste Index immer den Wert < 0 > hat. Ein Feld wird folgendermaßen definiert:
< datentyp > < variablenname > [ feldlänge ] ;
Beispiel:
int zahl [ 6 ], z1 ;
z1 = zahl [ 2 ] ;
Hier wird die Variable < zahl > mit 6 Werten definiert und der Variablen < z1 > das
Element mit dem Index < 2 > zugewiesen.
Zahl 12 -3 56 14 -10 23
Index 0 1 2 3 4 5
Wie groß ist ? z1 = zahl [ 2 ] ; _____
z1 = zahl [ 6 ] ; _____
42 2014 © Universität Duisburg-Essen
C-E lement : Fe lder
Bevor Sie eine neue Übungsaufgabe für die Anwendung von Feldern in Verbindung mit einer Schleife erhalten, erarbeiten Sie
bitte noch das nächste Kapitel „Textbearbeitung“, damit die Übungsaufgabe „Biegebalken“ (00/04) ergänzt und
abgeschlossen werden kann. Die Erweiterung erfordert die Lösung von 2 Teilaufgaben:
Die Eingabe der Werte soll in einer Funktion lies_double ( char text ) realisiert werden (07/01).
Der Benutzer soll am Ende des Programms entscheiden, ob er die Berechnung wiederholen möchte (07/01).
Wenn Sie den obigen Programmauszug für den Vergleich der 6 Lottozahlen
nunmehr mit Feldern in Verbindung mit einer Schleife durchführen, sieht daß so
aus:
int anzahl = 0 , zs [ 6 ] , zg [ 6 ] , i , j ;
< hier Definition der Zahlen >
for ( i = 0 ; i < 6 ; i = i + 1 )
{
for ( j = 0 ; j < 6 ; j = j + 1 )
{
if ( zs [ i ] == zg [ j ] ) anzahl = anzahl + 1 ;
}
}
Neben eindimensionalen Feldern gibt es auch mehrdimensionale Felder.
Die Längen der einzelnen Felder müssen nicht gleich lang sein. Hier ein
Anwendungsbeispiel aus der Mathematik:
int matrix [ 3 ] [ 5 ] , i , j ;
matrix [ 0] [ 1] [ 2] [ 3] [ 4]
[ 0] 12 -23 57 103 67
[ 1] -3 45 16 -5 71
[ 2] 39 42 87 91 -1
Ermitteln Sie: i = matrix [ 1 ] [ 3 ] ; i = ______
j = matrix [ 2 ] [ 0 ] ; j = ______
43 2014 © Universität Duisburg-Essen
C-E lement : Ze ichenke t ten - S t r ings
Sie glauben, daß Sie bisher noch nicht den Datentyp char sondern ausschließlich numerische Werte mit den Datentypen
float, double, int, short und long verarbeitet haben. Dieses ist nur bedingt richtig. In den von Ihnen benutzten printf-
Anweisungen kommen jeweils Texte < “ Text “ > vor, die man auch Zeichenketten oder string nennt und diese sind
vom Datentyp char. Während ein einzelnes Zeichen eine einfache Variable ist, werden Zeichenketten auch
Stringvariablen oder indizierte Variablen genannt. Letztere werden als Felder mit Index definiert. Syntax:
char buchstabe, zeile [ feldlänge ] ;
Bei der Zuordnung von Werten wird der Wert einer einfachen char-Variable jeweils mit einem einfachen < ´ > vor- und
hintenangestellten Anführungszeichen und der Wert einer indizierten char-Variablen mit dem doppelten < “ >
Anführungszeichen versehen. Belegung siehe Beispiel 1.
Beispiel 1:
char buchstabe ;
char zeichenkette [20] = {„Ingenieurinformatik“} ;
buchstabe = ‘x‘ ;
buchstabe = zeichenkette [ 7 ] ; = _____
zeichenkette [11] = ‘s‘ ;
In „Ingenieurinformatik“ wird der Buchstabe ____ geändert.
Beispiel 2:
char zeile [ 80 ] , zeichen ;
printf („ Gib Zeichen ein „ ) ;
scanf („ %c“ , &zeichen ) ;
fflush ( stdin ) ;
printf („ Gib Text ein “ ) ;
scanf („ %s“ , zeile ) ;
fflush ( stdin ) ;
Beim Einlesen von Werten für char-Variablen müssen Sie unterscheiden, ob es sich um ein einzelnes Zeichen oder
eine Zeichenkette handelt. Bei einem einzelnen Zeichen müssen Sie die Variable mit dem &-Zeichen versehen (s.
Beispiel 2), bei einer Zeichenkette auf keinen Fall, da dies ein Feld ist..
Bei der Übergabe von indizierten Variablen an eine aufgerufene Funktion muß in der Parameterliste der gerufenen
Funktion die Feldlänge nicht angegeben werden. Hier wird automatisch die Länge des belegten Textes als
Feldlänge angenommen. Wenn Sie trotzdem diese indizierte Variable mit einem Index versehen, so ist hier als
Übergabewert nur das einzelne Zeichen an der Position des angegeben Index gemeint.
44 2014 © Universität Duisburg-Essen
C-E lement : Ze ichenke t ten - S t r ings
Zur Bearbeitung von Zeichenketten gibt es in „C“ eine ganze Reihe von Funktionen. So kann z.B. mit der Funktion
strlen ( char < zeichenkette > ) die Anzahl der belegten Zeichen von < zeichenkette > ermittelt werden. Der Wert für
die Anzahl wird durch den Rückgabewert bereitgestellt. Die Leistungen der C-Funktionen für die String-Bearbeitung
erhalten Sie durch den Aufruf der Header-Datei
#include < string.h > ;
# include < string.h >
# include < stdio.h >
int zeichen_suche ( char, char [ ] ) ;
void main ( )
{
int anzahl ;
char zeichen = ‘e‘ ;
char zeile [13] = {„Testbeispiel“} ;
anzahl = zeichen_suche ( zeichen , zeile ) ;
printf („%s enthält %d * den Buchstaben %c“,
zeile, anzahl, zeichen ) ;
return ;
}
int zeichen_suche ( char zeichen, char text [ ] )
{
int z_anz = 0 , z_max , i ;
z_max = strlen ( text ) ;
for ( i = 0 ; i < z_max ; i = i + 1 )
{
if ( text [i] == zeichen ) z_anz = z_anz + 1 ;
}
return ( z_anz ) ;
}
Die Belegung von zeile [13] darf in dieser Form { ... } nur bei der Initialisierung erfolgen. In einer Anweisung dürfen nur
noch einzelne Zeichen, z.B. zeile [ i ] zugewiesen werden. Für die Zuweisung von Zeichenketten und die Anwendung
weiterer Bearbeitungen von Zeichenketten gibt es verschiedene Funktionen ( s. 07/02) .
45 2014 © Universität Duisburg-Essen
C-E lement : Ze ichenke t ten - S t r ings
Beachten Sie bitte, die folgende Besonderheit bei Textfeldern: Beim Einlesen von Texten wird bei einer Zeichenkette
seitens „C“ immer automatisch ein sogenanntes Null-Byte < ‚\0‘ > hinten angefügt, mit welchem das Ende der
belegten Zeichenkette markiert ist. Diese sogenannte Endmarke muß vorhanden sein, wenn Sie die Vielzahl der
vorhandenen C-Funktionen zur Textbearbeitung nutzen wollen, d.h., wenn Sie selbst programmintern eine Zeichenkette
belegen, müssen Sie selbst für die Zuordnung der Endmarke sorgen. Bei der Initialisierung (wie in Beispiel11) ist das
Setzen der Endmarke durch den Anwender nicht erforderlich.
Bei der Angabe der Groesse eines Textfeldes müssen Sie demnach immer ein Zeichen mehr angeben als im Text
enthalten ist.
char zeichenkette [20] = {„Ingenieurinformatik“} ;
Der Text sieht intern folgendermaßen aus:
Da Texte in C als Felder vom Typ char behandelt werden, ist die Textbearbeitung nicht so einfach wie bei anderen
Datentypen, wie beispielsweise bei int, double etc.
Es ist z. B. nicht möglich einer Textvariable in einem C-Programm einen neuen Wert zuzuweisen in der Form:
zeichenkette = „Neuer Text“; <- FALSCH !!!!
Index 0 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19
Zeichen I n g e n i e u r i n f o r m a t i k \0
46 2014 © Universität Duisburg-Essen
C-E lement : Ze ichenke t ten - S t r ings
Um Texte in C komfortabel bearbeiten zu können stehen eine Reihe von Hilfsfunktionen zur Verfügung. Die wichtigsten dieser
Funktionen werden im Folgenden vorgestellt.
Diese Funktionen stehen durch Einbinden der Headerdatei string.h zur Verfügung.
int strlen ( <Zeichenkette>); Ermittelt die Länge eines Textes (ohne das abschließende ‚\0‘)
int n;
char text[20] = „Ingenieurinformatik“;
n = strlen ( text);
Welchen Wert hat n?________________
int sprintf ( Zeichenkette, Format, ...); Schreibt den angegebenen Ausdruck in Zeichenkette. Analog zu der
bekannten Funktion printf. Diese Funktion kann benutzt werden,
um einer Zeichenkette einen neuen Text zuzuweisen.
anz = 3;
sprintf (text, „Es wurden %d Zahlen richtig getippt“, anz );
int strcpy (Text1, Text2); Kopiert den Inhalt von Text2 in die Zeichenkette Text1. Kann ebenfalls
für die Zuweisung benutzt werden.
strcpy (text, „IngInf“);
printf ( „%s“, text );
strcpy ( text, „Neuer, sehr langer Text“);
printf ( „%s“, text );
Welche Ausgabe erfolgt am Bildschirm?
int strcmp ( Text1, Text2); Vergleicht die beiden Zeichenketten Text1 und Text2. Das Ergebnis
des Vergleichs kann über den Rückgabewert ausgewertet
werden. Sind beide Texte identisch, liefert die Funktion den
Wert 0.
47 2014 © Universität Duisburg-Essen
C-E lement : Po in te r
Bevor das C-Element Pointer bzw. Zeiger vorgestellt wird, soll zunächst noch einmal auf den Unterschied zwischen
globalen und lokalen Variablen in den Beispielen A, B und C eingegangen werden.
A
int quadrat ( int ) ;
void main ( )
{
int i , j ; /* lokal */
i = 2 ;
j = quadrat ( i ) ;
return ;
}
/*** Funktion ******* /
int quadrat ( int n )
{
int i ; /* lokal */
i = n * n ;
n = 0 ;
return ( i ) ;
}
i = ___ j = ___
B
int quadrat ( int ) ;
int i ; /* global */
void main ( )
{
int j ;
i = 2 ;
j = quadrat ( i ) ;
return ;
}
/*** Funktion ******* /
int quadrat ( int n )
{
i = n * n ;
n = 0 ;
return ( i ) ;
}
i = ___ j = ___
C
int quadrat ( int ) ;
int i ; /* global */
void main ( )
{
int i , j ; /* lokal */
i = 2 ;
j = quadrat ( i ) ;
return ;
}
/*** Funktion ******* /
int quadrat ( int n )
{
int i ; /* lokal */
i = n * n ;
n = 0 ;
return ( i ) ;
}
i = ___ j = ___
1. In Beispiel A ist die Variable < i > jeweils nur als lokale Variable definiert, d.h., im Speicher gibt es 2
verschiedene Variablen mit dem Namen < i > und die Variable ist nur in der jeweiligen Funktion gültig.
2. In Beispiel B gibt es keine lokale Variable < i > sondern nur eine globale Variable < i >, d.h., beide Funktionen
greifen auf die gleiche Variable im Speicher zurück.
3. Im Beispiel C gibt es sowohl eine globale Variable < i > als auch jeweils 2 lokale Variablen < i >. Grundsätzlich
hat die lokale Variable < i > den Vorrang vor der globalen Variablen < i >.
Überlegen Sie nun, welche Ergebnisse die Variablen < i > und < j > erhalten.
48 2014 © Universität Duisburg-Essen
C-E lement : Po in te r
Wie Sie wissen, hat das Arbeiten mit Funktionen den Nachteil, dass Sie jeweils nur einen Wert zurück erhalten. Nun kommt
es aber häufig vor, daß Sie mehrere Werte in einer Funktion berechnen. Eine Funktion zur Berechnung der Schnittpunkte
ermittelt die Anzahl der Schnittpunkte und die zugehörigen x- und y-Koordinaten liefern, d.h., die Funktion müsste 5
Rückgabewerte liefern, was sie bekanntlich nicht kann. Dieses Problem mit Hilfe von globalen Variablen zu lösen, würde
schon bei mittelgroßen Programmen von dem Programmierer eine enorme Aufmerksamkeit verlangen.
Diese Problem ist in „C“ recht einfach gelöst worden, indem an die Funktion nicht der Inhalt einer Variablen sondern die
Adresse des Speicherplatzes übergeben wird, wo die Variable gespeichert ist. Mit Kenntnis der Adresse kann in jeder
Funktion auf den Inhalt des Speichers zugegriffen und damit auch der Wert der Variablen geändert werden, so daß an jeder
Stelle des Programms der aktuelle Variablen-Wert zur Verfügung steht. Diese Adressen werden pointer oder auch Zeiger
genannt.
Bei der Parameterübergabe an eine Funktion wird in der Argumentliste der gerufenen Funktion aus einer einfachen
Variablen durch den vorangestellten Adreßoperator & automatisch ein pointer. Sie kennen diese Vorgehensweise bereits
aus der Benutzung der Funktion scanf. In der Deklaration der Funktion wird in der Argumentliste zur Unterscheidung
gegenüber einfachen Variablen die Übergabe eines pointer durch den Dereferenzierungsoprator * gekennzeichnet.
Bei der Übergabe von indizierten Variablen (Feldern) ist die Zuordnung eines Adreßoperators nicht vorzusehen, da das
erste Element eines Feldes einer Adresse entspricht. Wenn Sie trotzdem ein Feld mit einen Adreß-operator versehen,
erzeugen Sie einen pointer auf einen pointer, was Sie eigentlich nicht wollen.
Sie müssen innerhalb einer größeren Anwendung wiederholt eine quadratische Gleichung lösen. Wegen der Häufigkeit
werden Sie dieses Problem sicherlich mit Hilfe einer Funktion lösen. Die allgemeine quadratische Gleichung lautet
: a*x2 + b*x + c = 0 .
Der Lösungsansatz für diese Gleichung lautet x1 = -p/2. + sqrt ( ( p / 2. ) 2 – q ) und
x2 = -p/2. - sqrt ( ( p / 2. ) 2 – q )
Wie Sie dem Lösungsansatz entnehmen können, kann eine quadratische Gleichung a) keine Lösung (imaginär), b) eine
Lösung (x1 = x2 ) oder c) zwei Lösungen (x1 ungleich x2) haben. Dies bedeutet, daß die Funktion nicht nur einen sondern
mehrere Werte zurückgeben muß. Wie Sie wissen, kann eine Funktion nur einen Wert zurückgeben. Das heißt, diese
Aufgabe liefert max. 3 Lösungswerte und läßt sich nur mit Hilfe von pointern lösen.
49 2014 © Universität Duisburg-Essen
C-E lement : Po in te r
/* DiesesHauptprogramm liest die Konstanten einer
quadratischen Gleichung ein und gibt die Lösung
dieser Gleichung aus. */
int quad_gl ( float*, float*, float, float, float ) ;
#include < stdio.h >
#include < math.h >
#define EPSI 0.000001
void main
{
float x1, x2, a1, a2, a3 ; /* Deklaration der Variablen */
int m = 0 , anzahl ;
while ( m != 3 ) /* Einlesen der Konstanten */
{
printf („\n\nLösung einer quadratischen Gleichung.
\nGib die Konstanten a, b, c ein. : “) ;
m = scanf („%f%f%f“, &a1, &a2, &a3 ) ;
fflush ( stdin ) ;
}
/* Berechnung der Lösungen der quadarat. Gleichung */
anzahl = quad_gl ( &x1, &x2, a1, a2, a3 ) ;
/* Ausgabe der Lösungen der quadrat. Gleichung */
if (anzahl > 0 )
{
printf („\n\n Die Gleichung \n\n
%-8.2f x^2 + %-8.2f x + %-8.2f \n\n
hat folgende Lösungen:\n\n
x1 = %-8.2f und x2 = %-8.2f \n\n“,
a1, a2, a3, x1, x2 ) ;
}
else /* Lösung imaginär */
{
printf („\n\n Die Gleichung \n\n
%-8.2f x^2 + %-8.2f x + %-8.2f \n\n
hat keine Lösung!\n\n“, a1, a2, a3 ) ;
}
return ;
}
/* Diese Funktion löst eine quadratische Gleichung
a, b, c sind die Konstanten der Gleichung
x1, x2 sind die Lösungen der Gleichung */
int quad_gl ( float *x1, float *x2, float a,
float b, float c )
{
int anzahl ; /* Deklaration der Variablen */
float p, q, wurzel_wert ;
p = b / a ; /* Berechnung der Hilfswerte */
q = c / a ;
wurzel_wert = ( p * p / 4. ) ^2 – q ;
/* Berechnung der Anzahl der Lösungen */
if (wurzel_wert < 0. ) anzahl = 0 ;
else if ( fabs (wurzel_wert ) < EPSI )
{
anzahl = 1 ;
*x1 = -p / 2. ;
*x2 = *x1 ;
}
else
{
anzahl = 2 ;
*x1 = -p / 2. + sqrt ( wurzel_wert ) ;
*x2 = -p / 2. – sqrt ( wurzel_wert ) ;
}
return ( anzahl ) ; /* Rückgabe der Anzahl */
}
Frage: Was bedeutet es und was ist zu tun, wenn alle oder einzelne
Werte (a1, a2, a3 ) = 0 sind?
50 2014 © Universität Duisburg-Essen
Syntax -Übers ich t
float breite, hoehe ;
double moment ;
int zahl, werte [ 12 ] ;
long entfernung ;
char buchstabe ;
char zeile [ 20 ] ; Variablendefinition
Einfache Variablen
[ ] = indizierte Variablen
int j = 2 ;
void main ( )
{
int i =3, n ;
n = i / j ;
return ;
} Funktion ohne Rückgabe
j = globale Variable
i , n =lokale Variablen
/* Diese Funktion muß
vorab definiert werden */
int division ( int a, int b )
{
int quotient ;
quotient = a / b ;
return ( quotient ) ;
} Funktion mit Rückgabewert
und /* Kommentarzeile */
#define PI 3.1415
void main ( )
{
float d = 5. , f ;
f = d * PI ;
return ;
} Konstantendefinition
#include < stdio.h >
int zahl ;
scanf ( „%d“, &zahl ) ;
fflush ( stdin ) ; Lese-Anweisung
float = %f
double = %lf
int = %d
long = %l
char = %c / %s
#include < stdio.h >
printf („Dies ist nur ein Text“) ;
printf („Zahl = %d“, zahl ) ;
printf („%d * %d = %d“, zahl, zahl, zahl*zahl ) ;
printf („Am Ende ist eine neue Zeile \n“ ) ; Ausgabe-Anweisungen
c = a * b / d ;
b = i > k && m < n || m == 0 Ausdrücke
(arithmetisch oder logisch )
if ( ausdruck ) < Anweisung ; > Einfache if-Anweisung ,
Anweisung wird ausgeführt, wenn
ausdruck ungleich Null oder wahr ist
if ( ausdruck )
{
< Anweisungen ; >
} Einfache if-Anweisung mit Block
if ( ausdruck ) < Anweisung 1 ; >
else < Anweisung 2 ; > Einfache if- / else-Anweisung
Wenn ausdruck wahr oder ungleich Null,
Anweisung 1 sonst Anweisung 2
if ( ausdruck )
{
< Anweisungen ; >
}
else
{
< Anweisungen ; >
} if- / else-Anweisung mit Block
if ( ausdruck 1 )
{
< Anweisungen ; >
}
else if ( ausdruck 2 )
{
< Anweisungen ; >
}
else
{
< Anweisungen ; >
} else if-Anweisung
51 2014 © Universität Duisburg-Essen
Syntax -Übers ich t
switch ( int )
{
case 1: < Anweisung 1 ; >
break ;
case 7 : case 4:
< Anweisung 2 ; >
< Anweisung 3 ; >
break ;
default: < Anweisung 4 ; >
} switch- / case-Anweisungen mit int-Wert-Vergleich
Anweisungen werden ausgeführt, wenn int-Wert = Konstante
switch ( char )
{
case ‘a‘: < Anweisung 1 ; >
break ;
case ‘h‘: case ‘n‘:
< Anweisung 2 ; >
< Anweisung 3 ; >
break ;
default: < Anweisung 4 ; >
} switch- / case-Anweisungen mit char-Wert-Vergleich
Anweisungen werden ausgeführt, wenn char-Wert = Zeichen
i = 0 ;
while ( i < 10 )
{
< Anweisungen ; >
i = i + 1 ;
} while-Schleife
Block = Wiederholungsbereich
i = 0 ;
do
{
< Anweisungen ; >
i = i + 1 ;
} while ( i < 10 ) do-Schleife
for ( i = 0 ; i < 10 ; i = i + 1 )
{
< Anweisungen ; >
} for-Schleife
float mittel ( float, float, float ) ;
void main ( )
{
float a =17.5, b = 23.45, c = -8.23, ergebnis ;
ergebnis = mittel ( a, b, c ) ;
return ;
} Rufende Funktion
float mittel ( float w1, float w2, float w3 )
{
float a ;
a = ( w1 + w2 + w3 ) / 3. ;
return ( a ) ;
} Gerufene Funktion: Berechnung des Mittelwertes Funktionen müssen vorab bekannt sein, siehe links oben.
52 2014 © Universität Duisburg-Essen
Syntax -Übers ich t
void main ( ) {
int i, summe = 0 ;
int zahl [ 6 ] = { 2, 4, -3, 6, 12, -1 } ;
for ( i = 0 ; i < 6 ; i = i + 1 )
{
summe = summe + zahl [ i ] ;
}
return ;
} Der Umgang mit indizierten Variablen (Feldern)
Ermittlung der Gesamtsumme aller Zahlen.
void main ( ) {
int i, summe = 0 ;
char bu = ‘i‘ , text [ 11 ] = {„informatik“} ;
for ( i = 0 ; i < 10 ; i = i + 1 )
{
if ( text [ i ] == bu ) summe = summe + 1 ;
}
return ;
} Der Umgang mit Text-Zeichen und Zeichenketten
Ermittlung, wie oft der Buchstabe i in Informatik vorkommt.
void kreis_werte ( float *, float * , float ) ;
#define PI 3.1415
void main ( )
{
float d = 18.5 , f, u, v ;
kreis_werte ( &f , &u , d ) ;
v = f / u ;
return ;
} Der Adreßoperator & macht die Variable f zur Adresse
void kreis_werte ( float *f, float *u, float d )
{
*f = d * d / 4. * PI ;
*u = d * PI ;
return ;
} Der Umgang mit pointern (Zeigern)
Das Zeichen * ist der Deferenzierungsoperator, d.h.,
er ist das Gegenstück zum Adreßoperator &.
53 2014 © Universität Duisburg-Essen
Ende