9. Vektoren (auch Felder/array)
Motivation Hat man mehrere Objekte gleichen Datentyps, so kann man sie explizit deklarieren, wenn die Anzahl bekannt ist double x1,x2,x3,x4; Nachteile: versagt, -wenn die Anzahl unbekannt/variabel ist -wenn das i-te Objekt benötigt wird und i beispielsweise eingelesen wird Dr. Norbert Spangler / Grundlagen der Informatik 10.11.2006 2
Motivation Ein Punkt X in einem ebenen Koordinatensystem ist gekennzeichnet durch 2 Koordinaten x 1 und x 2 Abspeicherung : Variante 1 : double x1,x2; -> 2 Variablennamen Alternative : 1 Vektor mit Namen x und Indizes 1 und 2 für Koordinaten -> x[1] und x[2] mit dem Indexoperator [ ] Dr. Norbert Spangler / Grundlagen der Informatik 10.11.2006 3
Motivation Vektoren werden also immer dann verwendet, wenn eine Liste gleicher Objekte verarbeitet werden soll. Ihre Anzahl ist variabel aber nach oben begrenzt. Die Objekte sind der Reihe nach bei 0 beginnend nummeriert. Dr. Norbert Spangler / Grundlagen der Informatik 10.11.2006 4
9.1 Definition von Vektoren Ein Vektor besteht aus mehreren Objekten identischen Datentyps mit einem gemeinsamen Namen. Die Elemente (Vektorelemente) sind hintereinander im Speicher abgelegt. Sie werden wie Variable deklariert, wobei zusätzlich über den Indexoperator die Anzahl der Elemente anzugeben ist: typ vektorname[anzahl]; anzahl ist eine ganzzahlige Konstante oder ein Ausdruck aus ganzzahligen Konstanten. Dr. Norbert Spangler / Grundlagen der Informatik 10.11.2006 5
Definition von Vektoren/Beispiele const int limit=10; double x[3], preise[5], dv[2*limit-1]; int nummer[limit]; x besteht aus 3, preis aus 5 und dv aus 19 Elementen von Typ double, nummer aus 10 Elementen vom Typ int. Dr. Norbert Spangler / Grundlagen der Informatik 10.11.2006 6
Definition von Vektoren Ein Vektor kann prinzipiell mit jedem Datentyp gebildet werden (wenige Ausnahmen wie z.b. void) Also auch Ampel kreuzung[20];//definiert 20 Elemente vom Typ Ampel Student liste[100];// definiert 100 Elemente vom Typ Student Bauteil schaltung[20];//definiert 100 Elemente vom Typ Bauteil Dr. Norbert Spangler / Grundlagen der Informatik 10.11.2006 7
Initialisierung Vektoren können bei der Definition mit Werten vorbelegt werden. Ohne Initialisierung ist die Belegung (wie bisher) unbekannt. Zur Initialisierung wird in geschweiften Klammern eine Liste mit Werten für die Vektorelemente angegeben : int zahl[3]={2,4,6}; double feld[5]={1.1,3.3,5.5,7.7,9.9}; Ergebnis: zahl[0]=2 zahl[1]=4 zahl[2]=6 feld[0]=1.1 feld[1]=3.3 feld[2]=5.5 feld[3]=7.7 feld[4]=9.9 Dr. Norbert Spangler / Grundlagen der Informatik 10.11.2006 8
Initialisierung Die Anzahl kann weggelassen werden. Sie ergibt sich dann automatisch aus der Anzahl der Elemente in der Initialisierungsliste int zahl[]={2,4,6}; double feld[]={1.1,3.3,5.5,7.7,9.9}; Ergebnis: zahl[0]=2 zahl[1]=4 zahl[2]=6 zahl hat 3 Elemente feld[0]=1.1 feld[1]=3.3 feld[2]=5.5 feld[3]=7.7 feld[4]=9.9 feld hat 5 Elemente Dr. Norbert Spangler / Grundlagen der Informatik 10.11.2006 9
Initialisierung Werden in der Initialisierungsliste weniger Elemente vorgegeben als definiert, so wird mit 0 aufgefüllt. int zahl[3]={2,4}; double feld[5]={1.1,3.3}; Ergebnis: zahl[0]=2 zahl[1]=4 zahl[2]=0 feld[0]=1.1 feld[1]=3.3 feld[2]=0.0 feld[3]=0.0 feld[4]=0.0 Dr. Norbert Spangler / Grundlagen der Informatik 10.11.2006 10
Initialisierung Werden in der Initialisierungsliste mehr Elemente vorgegeben als definiert, so werden die überzähligen Elemente in der Liste ignoriert. int zahl[3]={2,4,6,8,10}; double feld[5]={1.1,3.3,5.5,7.7,9.9,10.1,11,11}; Ergebnis: zahl[0]=2 zahl[1]=4 zahl[2]=6 feld[0]=1.1 feld[1]=3.3 feld[2]=5.5 feld[3]=7.7 feld[4]=9.9 Dr. Norbert Spangler / Grundlagen der Informatik 10.11.2006 11
9.2 Zugriff Der Zugriff auf die Vektorelemente erfolgt mittels des Indexoperators [] über einen Index: vektorname[index] index ist ein Ausdruck vom Typ int. Die Nummerierung der Vektorelemente beginnt bei 0 (!) und endet bei anzahl-1 D.h. die Elemente eines Vektors sind nummerierte Variable (indizierte Variable) Nummer <-> Index Dr. Norbert Spangler / Grundlagen der Informatik 10.11.2006 12
Zugriff const int limit=10; double x[3], preise[5], dv[2*limit-1]; int nummer[limit]; x[0] x[1] x[2] preis[0]... preis[4] dv[0]... dv[18] nummer[0] nummer[9] Dr. Norbert Spangler / Grundlagen der Informatik 10.11.2006 13
Index Beispiel: x[0]=22; // Der Name der Variablen ist x[0]. Der gespeicherte Wert ist 22. x[1]=44; // Der Name der Variablen ist x[1]. Der gespeicherte Wert ist 44. x[2]=77; // Der Name der Variablen ist x[2]. Der gespeicherte Wert ist 77. x[2]= x[1]+ x[0]+4; // Der Wert von x[2] ist jetzt 70 i=3; x[i-1]-=x[i-2]; // Der Wert von x[2] ist jetzt 26 for ( i=0;i<3;i++) cin>>x[i]; for ( i=0;i<3;i++) cout<< <<x[i]; Dr. Norbert Spangler / Grundlagen der Informatik 10.11.2006 14
9.3 Abspeicherung Die Abspeicherung erfolgt sequenziell hintereinander in einem zusammenhängenden Speicherbereich. Beispiel int zahl(5); 20 Bytes 4 Bytes = Länge von int zahl[0] zahl[1] zahl[2] zahl[3] zahl[4] Anfangsadresse Anfangsadresse+4 Anfangsadresse+20 Frage : was passiert bei zahl[5]= bzw. zahl[-1]=0???????? Dr. Norbert Spangler / Grundlagen der Informatik 10.11.2006 15
Indexüberschreitung Wenn beim Programmlauf ein Index ausserhalb des definierten Bereichs verwendet wird gibt es keine Fehlermeldung. Überprüfung von Bereichsüberschreitungen ist möglich (per Compiler) aber sehr aufwendig, da dann bei jedem Zugriff auf ein Vektorelement eine Überprüfung auf Indexüberschreitung stattfindet. -> man verzichtet üblicherweise darauf Dr. Norbert Spangler / Grundlagen der Informatik 10.11.2006 16
Beispiel // felder #include<iostream> using namespace std; void main() { int i,j=2,zahl[4],k=2; cout << endl << &k; cout << endl << &zahl; cout << endl << &j; cout << endl << &i; // vektor definieren for (i=-1;i<=4; i++) zahl[i]=i; // vektor ausgeben cout << endl << " Vektor zahl "; for (i=0;i<=3; i++) cout << endl << zahl[i]; // variable j,k ausgeben cout << endl << " k = " << k << " j = " << j <<endl; } Dr. Norbert Spangler / Grundlagen der Informatik 10.11.2006 17
Beispiel Dr. Norbert Spangler / Grundlagen der Informatik 10.11.2006 18
Beispiel //Was macht folgendes Programm? #include<iostream> using namespace std; void main() { int i; int zahl[4]; // vektor definieren for (i=1;i<=4; i++) { zahl[i]=i-1; cout << endl << i << " " << zahl[i]; } } -> Anhang Dr. Norbert Spangler / Grundlagen der Informatik 10.11.2006 19
9.4 Mehrdimensionale Vektoren C++ kennt (eigentlich) keine 2 oder mehrdimensionalen Vektoren sondern nur Vektoren von Vektoren (von Vektoren...) double matrix[2][3]={ {1.0,2.0,4.0},{1.5,-1.0,3.0} }; matrix ist ein eindimensionaler Vektor mit 2 Elementen. Diese sind eindimensionalen Vektoren mit 3 Elementen. Matrix hat also 2 Zeilen und 3 Spalten 1.0 2.0 4.0 1.5-1.0 3.0 Die Matrix wird damit zeilenweise abgespeichert Dr. Norbert Spangler / Grundlagen der Informatik 10.11.2006 20
Abspeicherung Reihenfolge: 00-01-02-10-11-12 #include <iostream> zeilenweise using namespace std; void main() { int mat[2][3]={{1,2,3},{4,5,6}}; } for (int i=0;i<2;i++) for ( int j=0;j<3;j++) cout << " mat[ <<i<< ][ <<j<< ] " <<mat[i][j] << " Adresse "<<&mat[i][j]<<endl; Dr. Norbert Spangler / Grundlagen der Informatik 10.11.2006 21
9.5 char-vektoren char puffer[5*1024]; // 5 KB Speicher zur Verwendung bei Datenübertragungen char name1[]= text ; // Vektor mit 5 Elementen char name2[]= { t, e, x, t, \0 }; Diese beiden Definitionen sind gleichwertig. Diese Technik der Abspeicherung von Zeichenketten ist in der Sprache C üblich. Daher werden diese Objekte auch C-Strings genannt. -> Es gibt auch die Klasse string (später genauer) #include <string> string s1= text ;// dies ist ein anderes Objekt Dr. Norbert Spangler / Grundlagen der Informatik 10.11.2006 22
char name1[]= text ; char name2[]= { a, \0 }; string s1= text,s2= a ; char-vektoren und die Klasse string //char name1=name2; // Speicherplatzproblem-> Verantwortung des Programmierers // Fehlermeldung = als Operator nicht erlaubt // Funktion erforderlich ( strcpy) cin >> setw(5)>>name1; // liest 5 Zeichen //strings s2=s1; // für strings möglich Strings sind aufwendiger (Overhead) aber eleganter, wenn viele Operationen notwendig sind. -> Kapitel string in Informatik 2 Dr. Norbert Spangler / Grundlagen der Informatik 10.11.2006 23
9.6 Elementare Techniken für Vektoren Grundsätzliches Ein Vektor wird üblicherweise so dimensioniert, dass alle erwarteten Aufgaben bearbeitet werden können, d.h. die Anzahl der vereinbarten Elemente muss grösser sein als die üblicherweise verwendeten Elemente. Beispiel : Vektor mit den Matrikelnummern der Studenten, die an der Klausur teilnehmen Erwartet ca. 130 -> etwas mehr müssen reserviert werden int matrikelnummer[200]; -> man benötigt für das Programm immer eine int-größe (anzahl), welche die aktuell verwendete Anzahl beinhaltet eine int-größe (limit), welche die reservierte Anzahl verwendet. Alternative : dynamische Vektoren (ev. später) Dr. Norbert Spangler / Grundlagen der Informatik 10.11.2006 24
Bisherige Deklaration : int matrikelnummer [200]; Verwendung von Konstanten Alternative : const int matrikelnummer_limit=200; int matrikelnummer[matrikelnummer_limit]; -> anstelle von : if ( matrikelnummer_anzahl<200) if ( matrikelnummer_anzahl<matrikelnummer_limit) ist besser Anstelle des Literals sollte man eine Konstante verwenden -> Vorteil : änderungsfreundlich bei Anpassung der Vektoren es muss nur an einer Stelle geändert werden Dr. Norbert Spangler / Grundlagen der Informatik 10.11.2006 25
Typische Aufgabenstellungen 1) Einlesen eines Vektors 2) Ausgabe eines Vektors 3) Summation der Elemente eines Vektors 4) Bestimmung des Maximums/Minimums der Elemente 5) Suche eines Elements in einem Vektor -> Übungen 6) Löschen eines Elements in einem Vektor 7) Einsortieren eines Elements in einem Vektor 8) Sortieren eines Vektors 9) Mischen zweier sortierter Vektoren Dr. Norbert Spangler / Grundlagen der Informatik 10.11.2006 26