|
|
||
|
|
||
| .. Strukturen - struct | ||
|
|
||
|
|
Strukturen sind eine Art Variable mit Untervariablen, bei der die Untervariablen unterschiedliche Typen besitzen können. Anders als bei der union (Variante) kann zu einem Zeitpunkt, jede dieser Untervariablen einen eigenen Wert besitzen.
Dementsprechend gross wird der benötigte Speicherraum einer Strukturvariablen. Bei der unten angegebenen Struktur sind das mindestens 11 Bytes, denn für den Integer i werden 2 Bytes, für die Fliesskommazahl x, 8 Bytes und für den Character c, 1 Byte benötigt.
Beispiel 1: |
|
struct {
int i;
double x;
char c;
} y, z;
|
||
|
|
|
|
|
|
|
|
|
|
|
|
struct zahl {
int i;
double x;
char c;
};
|
||
|
|
Im oberen Beispiel wird eine Struktur mit dem Namen Zahl deklariert. In der Folge kann der Name dieser Struktur wie ein Typbezeichner verwendet werden, so dass man zu beliebiger Zeit Variable von der Art dieser Struktur erzeugen kann. Beispielsweise ..
struct zahl y; oder an andere Stelle .. struct zahl z;
Jede dieser zwei Variablen y und z besitzt die Untervariablen i, x, und c, deren Variablentypen voneinander abweichen. |
|
|
|
|
|
|
|
|
|
typedef struct {
int i;
double x;
char c;
} zahl;
|
|
|
|
|
Wen es stört, dass man vor den Namen des Struktur-Variablentyps immer struct schreiben muss, der kann mit der Schlüsselwort typedef arbeiten. Dieses funktioniert ein Stück weit wie #define. Es wird also das gesamte Literal struct { ...} hinter dem Ausdruck zahl verborgen. Nun kann man so tun, als sei der Strukturname zahl ein eigenständiger Variablentyp, denn man darf schreiben ..
zahl y; oder an andere Stelle .. zahl z;
.. was indirekt dem Beispiel 1 ähnlich ist. Jede der zwei Variablen y und z besitzt die Untervariablen i, x, und c, deren Variablentypen voneinander abweichen. |
|
|
|
|
|
|
|
Deklaration und Initialisation Schon bei der Deklaration können den Untervariablen einer Strukturvariablen Werte übergeben werden.
Beispiel: zahl z = {0x1234, 1234.57, 0xC3}; bei neueren Compilern kann es notwendig sein, um jede Untervariable geschweifte Klammern zu setzen, wodurch der Ausdruck dann wie folgt aussieht. zahl z = {{0x1234}, {1234.57}, {0xC3}};
Nach dieser Zuweisung werden die Variablen folgende Werte besitzen .. z.i = 0x1234, z.x = 1234.57, z.c = 0xC3 |
|
|
|
|
|
|
|
Bei Strukturen ist es (anders als bei Varianten) möglich, jeder Untervariablen gleichzeitig einen eigenen Wert einzuschreiben. Das nachfolgende Programm zeigt diese Eigenschaften aus der Warte des Programmierers.
Ein Beispielprogramm
|
|
|
|
|
|
// struct.cpp
// ------------ Version 17.06.2007
// Borland IDE C++ 3.1 oder 5.02
// Model: SMALL
// Char: unsigned
// bearbeitet: www.GoBlack.de, D.Schwarzer
// Hardware: jeder DOS-PC
#include <stdio> // für printf()
#include <conio> // für getch()
// typedef struct {int i; double x; char c;} zahl; // Alternative
struct zahl {int i; double x; char c;};
// Dieser Programmteil liest die 11 Bytes der übergebenen Variablen
// z vom Typ (structur) zahl und gibt sie samt Anfangsadresse
// aufeinanderfolgend zum Bildschirm aus.
void scan_struct(zahl z)
{
int n=0;
char* m;
m = (char*)&z;
printf ("\n Adr von z: %X - Inhalt: ", &z);
for (n=sizeof(z)-1; n>=0; n--){printf("%02X", *(m+n));}
}
// das Beispielprogramm ermittelt für die Variable z und
// jede ihrer Untervariablen z.i, z.x, z.c die Anzahl der
// belegten Bytes, sowie deren Anfangsadressen im Speicher
// dann wird jeder der drei Untervariablen ein legaler
// Wert zugewiesen und beobachtet zu welchem Resultat das
// bei der Füllung der Struktur und ihrer Untervariablen
// führt.
void main (void)
{
// Deklaration und Definition einer Variablen z vom neuen Typ
// (struktur)zahl
struct zahl z={0,0,0};
// Anzahl der belegten Bytes im Speicher und ..
// Anfangsadresse der Variablen
printf ("\nbelegte Bytes im Speicher / AnfangsAdresse");
printf ("\nz = %2d Adr: %04Xh", sizeof(z), &z);
printf ("\nz.i = %2d Adr: %04Xh", sizeof(z.i), &z.i);
printf ("\nz.x = %2d Adr: %04Xh", sizeof(z.x), &z.x);
printf ("\nz.c = %2d Adr: %04Xh", sizeof(z.c), &z.c);
printf ("\n-----");
// Wert für z.i => noch keine Werte für z.x und z.c
z.i = 0x1234;
scan_struct(z);
printf ("\n Wert fuer IntegerVariable z.i");
printf ("\nInhalt hex z.i = %04Xh", z.i);
printf ("\nInhalt float z.x = %g", z.x);
printf ("\nInhalt hex z.c = %02Xh", z.c);
printf ("\n-----");
// Wert für z.x => noch kein Wert für z.c
z.x = 1234.57;
scan_struct(z);
printf ("\n Wert fuer FliesskommaVariable z.x");
printf ("\nInhalt hex z.i = %04Xh", z.i);
printf ("\nInhalt float z.x = %g", z.x);
printf ("\nInhalt hex z.c = %02Xh", z.c);
printf ("\n-----");
// Wert für z.c => Struktur ist gefüllt
z.c = 0xC3;
scan_struct(z);
printf ("\n Wert fuer CharacterVariable z.c");
printf ("\nInhalt hex z.i = %04Xh", z.i);
printf ("\nInhalt float z.x = %g", z.x);
printf ("\nInhalt hex z.c = %02Xh", z.c);
getch();
}
|
|
|
|
|
|
|
|
|
|
|
|
|
Der Ausgabebildschirm des obigen Programms. Zu beachten ist, dass die Zuweisung von Adressen der Variablen zur Laufzeit erfolgt, .. sie können also bei jedem Lauf des Programms andere Werte annehmen.
An diesem Beispiel kann auch der Unterschied zwischen der Codierung von Fliesskommazahlen im Gegensatz zu der von Integerzahlen betrachtet werden. Setzen Sie mal beide Werte gleich, also z.i=1234 und z.x=1234. Während die Integerzahl mit 1234 im Listing gut auszumachen ist, ergibt sich für die Fliesskommazahl 4093480000000000. Aus diese Darstellung würde man nicht unmittelbar darauf schliessen das hier die Zahl 1234 steht. |
|
|
|
|
|
|
|
|
|
|
|
.de