Probleme mit wchar_t Array



  • Hallo,

    ich habe beim Programmieren ein kleines Problem.

    wchar_t *files[255]={};
    ..
    ....
    hFind = FindFirstFile(szDir, &ffd);
    .......
    ..
    do
    {
    if (ffd.dwFileAttributes & FILE_ATTRIBUTE_DIRECTORY)
    {
    //nicht relevant
    }
    else
    {
    files[i]=ffd.cFileName; //abspeichern im Array
    MessageBox(NULL, files[i], TEXT("Testfenster"),
    MB_ICONINFORMATION|MB_OKCANCEL|MB_DEFBUTTON1);
    i++;
    }
    }
    while (FindNextFile(hFind, &ffd) != 0);
    

    Das ist ein Ausschnitt aus einer Funktion, die Daten aus einem Ordner nacheinander ausliest.
    In diesem Teil wird der Dateiname in einem Array gespeichert. Alles funktioniert auch soweit ganz gut bis auf die Tatsache, dass das Array von 0 bis i-1 mit dem zuletzt gefundenen Dateinamen überschrieben wird. Somit steht am Ende der while-Schleife in dem Array immer der gleiche Eintrag.
    Was mache ich falsch? Hoffe jemand hier kann mir da helfen.

    MfG



  • Naja, Du biegst alle Zeiger Deines Arrays auf ffd.cFileName. Und dieses wird bei jedem Aufruf von FindNextFile mit dem nächsten gefundenen Filenamen überschrieben. Am Ende der while-Schleife steht in ffd.cFileName der letzte gefundene Dateiname, und alle Deine Zeiger in Deinem Array zeigen auf ffd.cFileName.



  • Verstehe. Daran hab ich jetzt nicht gedacht gehabt.
    Danke. Wenns um Zeiger geht, verknotet sich mein Gehirn 🙂

    Jetzt hab ichs auch hinbekommen.

    MfG



  • Ok, neues Problem. Aber erstmal zur Lösung des alten.

    anstatt

    WIN32_FIND_DATA ffd;
    

    habe ich nun ein Array daraus gemacht und im weiteren Verlauf natürlich entsprechend angepasst.

    WIN32_FIND_DATA ffd[255];
    

    Im weiteren Verlauf des Programms erstelle ich einige Knöpfe

    for(int m=0;m<tracks;m++)
    {
    	DestroyWindow(hButtons[m]);
            hButtons[m] = CreateWindow(  TEXT("button"),
    		         (LPCWSTR)files[m],
                             WS_VISIBLE | WS_CHILD | WS_BORDER,
    			 0,0,0,0,hwnd,(HMENU)m,	NULL,NULL);
    }
    break;
    

    Die werden mir auch Korrekt angezeigt. Der Text der Knöpfe entspricht dem entsprechenden Dateinamen. files[] wird nicht mehr verändert (eigentlich)

    Wenn ich nun einen Knopf anklicke passiert folgendes

    case WM_COMMAND:
    {
    	if(LOWORD(wParam)>=0 && LOWORD(wParam)<=255)
    	{
    		int pressed=LOWORD(wParam);
    
    		MessageBox(NULL, files[pressed], TEXT("Testfenster"),
    	        MB_ICONINFORMATION | MB_OKCANCEL | MB_DEFBUTTON1);
    	}
            case (HMENU)256:    //Knopf zum Datenauslesen
            {
    ....
    .......
    

    Wenn ich nun die Fenster anklicke, erscheint die MessageBox mit den Dateinamen als Text. Außer beim ersten Knopf. Da steht dann irgendetwas drinen, aber nicht der Dateiname. Der entsprechende Knopf allerdings hat den richtgen Text erhalten, also muss irgendow zwischendurch die erste Zeile in files[] gelöscht worden sein.
    Wieso/wie/wo wurde der erste Eintrag gelöscht. Und warum nur der Erste?

    MfG



  • Konnte mein Problem doch selbst lösen.

    WIN32_FIND_DATA ffd[255];

    habe ich nun global deklariert. Davor war es in einer Switch-Case Anweisung. Wenn man da raus geht, wird wohl die erste Zeile des Arrays gelöscht.
    Warum versteh ich aber immernoch nicht bzw. kanns mir denken, bin mir da aber nicht sicher. Falls mir das einer genauer sagen kann, wäre ich sehr dankbar.

    MfG



  • Vielleicht solltest Du bei Deiner ersten Version bleiben, und die Filenamen in Dein Array kopieren:

    wchar_t *files[255]={};
    ..
    ....
    hFind = FindFirstFile(szDir, &ffd);
    .......
    ..
    do
    {
        if (ffd.dwFileAttributes & FILE_ATTRIBUTE_DIRECTORY)
        {
            //nicht relevant
        }
        else
        {
            //Speicher besorgen
            files[i]=malloc(sizeof(wchar_t) * (lstrlen(ffd.cFileName) + 1));
            //und String kopieren
            lstrcpy(files[i], ffd.cFileName);
            //files[i]=ffd.cFileName; //abspeichern im Array
            MessageBox(NULL, files[i], TEXT("Testfenster"),
            MB_ICONINFORMATION|MB_OKCANCEL|MB_DEFBUTTON1);
            i++;
        }
    }
    while (FindNextFile(hFind, &ffd) != 0);
    

    Falls der allokierte Speicher irgendwann im Programmverlauf nicht mehr benötigt werden sollte, solltest Du ihn natürlich wieder freigeben.


Anmelden zum Antworten