Char-Array richtig terminieren
-
Hallo
In einer Whileschleife wird mein Feld mehrfach immer wieder mit Dateinamen überschrieben.
Doch leider habe ich dabei das Problem, dass wenn im vorhergehenden Durchlauf ein sehr langer Name dabei war und im darauf folgenden ein sehr kurzer Name, dass dann hinter diesem Namen noch der Rest des alten steht.
Habe es auch schon mit dem anhängen von \0 probiert, aber kein Erfolg.strcpy(FileLocation, FileDir); strcat(FileLocation, pDir->d_name); strcat(FileLocation, "\0");
Ich hatte mir gedacht, das Feld mit jedem neuen Durchlauf mit 0 zu initialisieren aber leider weiß ich dafür die Syntax nicht.
Vielen Dank Euch!
-
*FileLocation = 0;
-
strcat/strcpy nullterminieren von selbst. Aber bist du dir auch sicher, dass du nicht über die Grenzen des Feldes hinausschreibst?
Das Feld auf 0 zu setzen geht mittels man: memset:
memset(feld, '\0', groesze_des_felds);
-
Er könnte mal die komplette Schleife posten, da ist was anderes faul.
-
Hallo Danke für die Antworten.
Habe gerade gemerkt, dass ich diese 0-Terminierung überhaupt nicht brauche, denn strcat sorgt ja wirklich schon für \0 am Ende.
Das Problem, über welchem ich grüble steckt woanders und zwar:
Mein Prog führt eine rekursive Ordnersuche durch. So im Stammordner läuft noch alles paletti, aber wenn sich das Programm dann eine Hierarchieebene weiter nach unten gearbeitet hat, wird seltsamerweise an die Variable, die das Verzeichnis enthält, der aktuelle Dateiname, der gefundenen Datei angehängt.
Und dass, obwohl sich keine Schreiboperation auf diese Variable im Programm an dieser Stelle befindet.Diese while-Schleife ist Teil der Funktion DirSeek.
while ((pDir=readdir(pFileDir)) != NULL){ if(strcmp(pDir->d_name,"..")!=0 && strcmp(pDir->d_name,".")!=0){ strcpy(FileLocation, FileDir); strcat(FileLocation, pDir->d_name); printf(" %s", FileLocation); if(IsDir(FileLocation)){ FNAME Temp={0}; strcpy(Temp, FileDir); cout<<"\n\t|||ORDNER||| "; strcat(FileDir,pDir->d_name); cout<< FileDir<<"\n"; DirSeek(FileLocation, cntA, cntD); strcpy(FileDir, Temp); cout<<"\n\nGerade geoeffnet: "<<FileDir<<endl; } else { cout<< "\tDATEI "; cout<< cntD<<" "; cntD++; cout<< pDir->d_name <<"\n"; //######### MP3-Dateien finden ####################################// int NLength = strlen(FileLocation); if (strcmp(&FileLocation[NLength-4],".mp3")==0|| strcmp(&FileLocation[NLength-4],".wma")==0){ cout<<strlen(FileLocation)<<endl; strcpy(pMp3_List->Pfad,FileLocation); cntA++; if ( (pMp3_List->Next = (struct Mp3_List *) malloc(sizeof(struct Mp3_List))) == NULL ) { fprintf(stderr, "Kein Speicherplatz für weitere MP3-Datei vorhanden!\n"); EXIT_FAILURE; } pMp3_List = pMp3_List->Next; z++; } } }
Die Funktion IsDir überprüft ob es sich um eine Datei oder einen Ordner handelt.
Der seltsame Vorgang ereignet sich ganz oben in dem Bereich der 3 Zeilen, die die Variable FileLocation erstellen.
Wie gesagt, das klappt wunderbar, bis der rekursive Aufruf der Funktion kommt.
-
Ich bin jetzt zu faul bei der Hitze ...
Aber
if(strcmp(pDir->d_name,"..")!=0 && strcmp(pDir->d_name,".")!=0){
geht auch einfacher:
if( *pDir->d_name =='.'){
-
PlattitüdenAbonennt schrieb:
Der seltsame Vorgang ereignet sich ganz oben in dem Bereich der 3 Zeilen, die die Variable FileLocation erstellen.
Du musst mehr von dem Code zeigen, damit man sehen kann, wie die ganzen Variablen definiert sind, und was davon lokal oder global ist.
Scheppertreiber schrieb:
geht auch einfacher:
Tut aber nicht dasselbe.
-
@scheppertreiber
Wie soll denn das bitte hinhauen?So hier noch mal der gesamte Code:
#include <cstdlib> #include <iostream> #include <dirent.h> #include <direct.h> #include <cstdio> #include <windows.h> #include <conio.h> #include <string.h> #include <sys/stat.h> #include <sys/types.h> #include <unistd.h> #define LengthName 300 using namespace std; typedef char FNAME[LengthName]; FNAME FileLocation; bool IsDir(char* pFName) { struct stat File_Attribut; File_Attribut.st_mode = 0; stat(pFName, &File_Attribut); return ((File_Attribut.st_mode & S_IFDIR) == S_IFDIR); } struct Mp3_List{ FNAME Pfad; struct Mp3_List *Next; } *Anfang=NULL, *pMp3_List; struct list* DirSeek (char *FileDir, int cntA, int cntD){ struct dirent *pDir; struct stat File_Attribut; int z=1; DIR *pFileDir; DIR *pDirTemp; while(!(pFileDir=opendir(FileDir))) { cout<<"Nix Ordner, ein neues muss her! /: "; cin>>FileDir; pFileDir=opendir(FileDir); } if(Anfang == NULL) { if( (Anfang = (struct Mp3_List *) malloc(sizeof(struct Mp3_List))) == NULL ) { cout<< "Kein Speicherplatz für anfang vorhanden!\n"; } pMp3_List = Anfang; } FileDir= strcat(FileDir,"\\"); while ((pDir=readdir(pFileDir)) != NULL){ if(/*strcmp(pDir->d_name,"..")!=0 && strcmp(pDir->d_name,".")!=0*/){ strcpy(FileLocation, FileDir); strcat(FileLocation, pDir->d_name); if(IsDir(FileLocation)){ FNAME Temp={0}; strcpy(Temp, FileDir); cout<<"\n\t|||ORDNER||| "; strcat(FileDir,pDir->d_name); cout<< FileDir<<"\n"; DirSeek(FileLocation/*, pFileDir*/, cntA, cntD); strcpy(FileDir, Temp); cout<<"\n\nGerade geoeffnet: "<<FileDir<<endl; } else { cout<< "\tDATEI "; cout<< cntD<<" "; cntD++; cout<< pDir->d_name /*Mp3_List->Pfad*/<<"\n"; int NLength = strlen(FileLocation); if (strcmp(&FileLocation[NLength-4],".mp3")==0|| strcmp(&FileLocation[NLength-4],".wma")==0){ cout<<strlen(FileLocation)<<endl; strcpy(pMp3_List->Pfad,FileLocation); cntA++; if ( (pMp3_List->Next = (struct Mp3_List *) malloc(sizeof(struct Mp3_List))) == NULL ) { fprintf(stderr, "Kein Speicherplatz für weitere MP3-Datei vorhanden!\n"); EXIT_FAILURE; } pMp3_List = pMp3_List->Next; z++; } } } } return (struct list*)Anfang; } void Output_Copy(struct Mp3_List){ cout <<"\n"; cout.fill('#');cout.width(50); cout<<"\n"; cout <<"\n\tGefundene Audio-Dateien\n\n"; cout.fill('#');cout.width(50); cout<<"\n"; cout <<"\n"; int k=1; pMp3_List = NULL; pMp3_List = Anfang; while (pMp3_List->Next!=NULL){ cout <<" Index"<<" "<<k<<" "<<pMp3_List->Pfad <<endl; pMp3_List = pMp3_List->Next; k++; } } // ###### MAIN ####################### int main(){ FNAME FileDir="c:\\abc"; int pIndex=0; DIR *pFileDir; int MP3_Counter =0; int Data_Counter =1; DirSeek(FileDir,MP3_Counter,Data_Counter); Output_Copy(*Anfang); getch(); }
-
Bei der Rekursion übergibst du deine globale Variable FileLocation, d.h. FileDir und FileLocation verweisen in den rekursiven Aufrufen auf denselben Puffer. Was du an dem einen änderst, passiert auch mit dem anderen.
-
Danke, hat funktioniert.