Problem mit mehrdimensionaler Array-Größe



  • Hi Leute,

    ich habe in meinem Programm ein zweidimensionales Array, welches ein Spielfeld darstellt. Bei der Deklaration eines Arrays müssen die Indizes konstant sein, soviel habe ich ja schon gelernt, aber gibt es eine Möglichkeit diese Werte irgendwie zu ändern?
    Ich möchte gern eine Option bereitstellen, dass man die Länge und die Breite des Spielfeldes verändern kann, aber wie geht das? Ich habe da schon an Zeiger gedacht und auch schon ausprobiert, aber ich steig da nicht ganz dahinter. Könntet ihr mir da einen Ansatz geben? Ich würde mich über Hilfe freuen.

    MfG Apo



  • Hallo

    in dem du das Feld mit new dynamisch erstellst

    int x* = new int[10]; // erstellt ein dynamisches Array mit 10 Elementen
    ...
    delete[] x; // Löscht das Array mach Gebrauch wieder
    

    allerdings ist es in C++ einfacher, wenn du std::vector nimmst, das diese dynamsiche Verwaltung für dich übernimmt.

    bis bald
    akari



  • Hi,

    ich habe das nun mal mit dem new gemacht, aber der bringt mir nun komische Fehlermeldungen, die ich nicht so ganz verstehe. Hier mein Quellcode:

    // Header-Dateien
    #include <iostream>
    using namespace std;
    
    int main()
    {
    	// deklarieren der Variablen
    	int  breite     = 0;
    	int  hoehe      = 0;
    	int* pSpielfeld = NULL;
    	int  i, j;
    
    	// Eingabe
    	cout << "Breite: ";
    	cin >> breite;
    	cout << "Hoehe: ";
    	cin >> hoehe;
    
    	// Eingabeauswertung
    	if(breite < 0 || breite > 9 && hoehe < 0 || hoehe > 9)
    	{
    		cout << "Du hast eine ungueltige Eingabe getaetigt." << endl;
    		cin.get(); cin.get();
    		return 1;
    	}
    	else
    	{
    		// Speicher reservieren
    		pSpielfeld = new int[breite][hoehe];   // Hier kommt ein Fehler
    
    		// testen ob Speicher reserviert werden konnte
    		if(pSpielfeld)
    		{
    			// Spielfeld durchlaufen
    			for(i = 0; i < hoehe; i++)
    			{
    				for(j = 0; j < breite; j++)
    					pSpielfeld[j][i] = 0;   // Hier kommt noch einer
    				cout << endl;
    			}
    
    			// Spielfeld ausgeben
    			for(i = 0; i < hoehe; i++)
    			{
    				for(j = 0; j < breite; j++)
    					cout << pSpielfeld[j][i] << " ";   // und weil es so schön ist, noch einer
    				cout << endl;
    			}
    
    			// Speicher wieder freigeben
    			delete[] pSpielfeld;
    		}
    	}
    
    	cin.get(); cin.get();
    	return 0;
    }
    

    Ich hoffe man kann erstmal erkennen, was ich machen möchte. Ich möchte halt ein zweidimensionales Array erzeugen, indem in den Feldern eine 0 steht. Die Breite und die Höhe des Feldes soll vom Anwender eingestellt werden können. Wenn ich den oben genannten Quellcode kompilieren, dann bekomme ich folgende Fehlermeldungen:

    --------------------Konfiguration: Test - Win32 Debug--------------------
    Kompilierung läuft...
    dynArray.cpp
    W:\test\dynArray.cpp(29) : error C2540: Kein konstanter Ausdruck als Feldgrenze
    W:\test\dynArray.cpp(29) : error C2440: '=' : 'int (*)[1]' kann nicht in 'int *' konvertiert werden
            Die Typen, auf die verwiesen wird, sind nicht verwandt; die Konvertierung erfordert einen reinterpret_cast-Operator oder eine Typumwandlung im C- oder Funktionsformat
    W:\test\dynArray.cpp(38) : error C2109: Index benoetigt ein Feld oder einen Zeigertyp
    W:\test\dynArray.cpp(38) : error C2106: '=' : Linker Operand muss ein L-Wert sein
    W:\test\dynArray.cpp(46) : error C2109: Index benoetigt ein Feld oder einen Zeigertyp
    Fehler beim Ausführen von cl.exe.
    
    Test.exe - 5 Fehler, 0 Warnung(en)
    

    Laut einem Buch, welches ich mir gekauft habe, müssten die Indizes in den eckigen Klammern nun auch flexibel sein können, also können eingegeben werden und müssen nicht mehr konstant sein. Könnt ihr mir da helfen und mir sagen wo mein Fehler liegt? Wäre sehr nett von euch.

    MfG Apo



  • Wenn du einen Mehrdimensionalen Array haben willst musst du folgendes machen:

    int **xy;
    *xy = new int[10];
    for(int i = 0; i < 10; i++)
    {
        xy[i] = new int[10];
    }
    
    //irgendwas machen
    
    for(int i = 0; i < 10; i++)
    {
        delete[] xy;
    }
    
    delete[] *xy;
    


  • eher so

    for(int i = 0; i < 10; i++)
    {
        delete[] xy[i];
    }
    


  • Okay..., danke, für eure schnelle Antwort. Ich werde es gleich mal ausprobieren. Werde mich dann nochmal melden, ob es geklappt hat, aber wenn ihr es sagt, dann wird das schon stimmen. 😉

    EDIT:

    Also ich habe es nun so gemacht, wie ihr es oben beschrieben habt. Das Programm lässt sich nun kompilieren, aber nachdem ich die Werte für das Array eingetragen habe, z.B. 7 Felder für die Breite und 5 für die Höhe, dann kommen erstmal zwei Fehlermeldungen, dass die Anweisung 0x00401210 auf den Speicher 0x00000000 verweist und direkt danach kommt noch ein Fenster, und zwar das die Ausnahme "unknown software exception" (...) in der Anwendung an der Stelle ... aufgetreten ist.

    Ich vermute, dass ich das Array falsch durchlaufe und an irgendwelchen Feldern eine 0 reinschreiben möchte. Könnt ihr mir sagen, ob meine Vermutung richtig ist und wie ich das Array dann am besten durchlaufe? Danke schonmal...

    MfG Apo



  • Mach mal aus

    // Spielfeld durchlaufen
                for(i = 0; i < hoehe; i++)
                {
                    for(j = 0; j < breite; j++)
                        pSpielfeld[j][i] = 0;   // Hier kommt noch einer
                    cout << endl;
                }
    

    das hier:

    // Spielfeld durchlaufen
                for(j = 0; j < breite; j++)
                {
                    for(i = 0; i < hoehe; i++)
                        pSpielfeld[j][i] = 0;   // Hier kommt noch einer
                    cout << endl;
                }
    

    Könnte daran liegen, zumindest ist die Art, so ein 2-dimensionales Array zu durchlaufen, ungewöhnlich wie du es hast. Habe aber leider gerade nichts zum Testen zu Hand. Falls es immer noch nicht geht, poste mal nochmal deinen ganzen verbesserten Code, dann wird der Fehler evtl schon bei deiner Speicherplatzallokierung (new) liegen.



  • Guten Morgen Leute,

    also ich es nun mal so gemacht, wie du es mir gesagt hast, aber es funktioniert leider immer noch nicht. Hier ist nochmal mein Quellcode:

    // Header-Dateien
    #include <iostream>
    using namespace std;
    
    int main()
    {
        // deklarieren der Variablen
        int  breite     = 0;
        int  hoehe      = 0;
        int** pSpielfeld = NULL;
        int  i, j;
    
        // Eingabe
        cout << "Breite: ";
        cin >> breite;
        cout << "Hoehe: ";
        cin >> hoehe;
    
        // Eingabeauswertung
        if(breite < 0 || breite > 9 && hoehe < 0 || hoehe > 9)
        {
            cout << "Du hast eine ungueltige Eingabe getaetigt." << endl;
            cin.get(); cin.get();
            return 1;
        }
        else
        {
            // Speicher reservieren
            *pSpielfeld = new int[breite];
    		for(i = 0; i < hoehe; i++)
    			pSpielfeld[i] = new int[10];
    
            // testen ob Speicher reserviert werden konnte
            if(pSpielfeld)
            {
                // Spielfeld durchlaufen
                for(j = 0; j < breite; j++)
                {
                    for(i = 0; i < hoehe; i++)
                        pSpielfeld[j][i] = 0;
                    cout << endl;
                }
    
                // Spielfeld ausgeben
                for(j = 0; j < breite; j++)
                {
                    for(i = 0; i < hoehe; i++)
                        cout << pSpielfeld[j][i] << " ";
                    cout << endl;
                }
    
                // Speicher wieder freigeben
    			for(i = 0; i < hoehe; i++)
    				delete[] pSpielfeld[i];
    
                delete[] *pSpielfeld;
            }
        }
    
        cin.get(); cin.get();
        return 0;
    }
    

    Ich hoffe das ihr versteht, was ich mit dem Programm bezwecken möchte. Danke schonmal...

    MfG Apo



  • mach doch mal aus dem

    *pSpielfeld = new int[breite];
    

    ein

    pSpielfeld = new int*[breite];
    


  • Und lass beim letzten delete-Befehl das * weg.



  • und schau dir mal in der Win32 FAQ an, wie man die Konsole "besser" geöffnet lässt (@cin.get(),cin.get()) 😉



  • Hi,

    hat zwar nix mit deinem Problem direkt zutun, aber den Else-Zweig nach dem return 1 kannste dir schenken. Entweder bricht dein Programm die Main Funktion ab, oder der Code nach dem Anweisungsblock der If-Abfrage wird ausgeführt.

    Gruß Chris



  • Apocalypse schrieb:

    // Speicher reservieren
        *pSpielfeld = new int[breite];
        for(i = 0; i < hoehe; i++)
            pSpielfeld[i] = new int[10];
    

    Entweder du initialisierst mit new *int[hoehe], oder du läufst die Schleife nur bis breite durch. Sonst krachts bei der Ausführung, wenn hoehe > breite.



  • Hey..., danke es funktioniert nun. Es lag wirklich an den beiden Fehlern!

    MfG Apo *freu*


Anmelden zum Antworten