Adresskarteikarten, C++ , Stream! Hilfe ^^
-
Hi @ all User,
Habe da nen Problem:
Fehler beim Laden, es werden nur leere Strings geladen, außer der Postleitzahl, die wird 0 !
scheinbar werden die werte nicht übergeben!Speichern, es legt keine neue Datei an! Quasie sollte das meines erachtens werden wie einen Neuen Datensatz erzeugen, + Den Datensatzinhalteinfügen!
Datensatzzählen, habe versucht ans ende zu springen und mit der tellg funktion wollte ich die größe erfahren (soll ja die gesamtgröße zurückgeben) und diese wollte ich dann durch den Datensatz selbst Teilen Quasie ganz simpel um den aktuellen Datensatz zu erfahren jedoch liefert tellg mir imme -1 zurück KP warum!
Hier das Programm:
Das Progie (Borland C++ Buielder 6)Und hier der QuellCode:
Meine Header Datei
#include <fstream.h> //Datensatzstruktur für Adresskartei definieren! struct pAdrDatensatz { char Nachname[32]; char Vorname[17]; char Strasse[42]; char Nr[7]; char Ort[27]; unsigned int PLZ; char Tel[22]; char email[32]; char Geburtsdatum[12]; }; //Datensatz pAdrDatensatz myDat; //Datei -speichern -laden AnsiString DateiName; //Stream ofstream dat_io; ifstream dat_in; //Datei offen ? bool Dat_Open;Konstruktor
//--------------------------------------------------------------------------- __fastcall TForm1::TForm1(TComponent* Owner) : TForm(Owner) { //Datei offen == false (geschlossen) Dat_Open=false; //Verzeichnis der Anwendung ermitteln AnsiString Pfad=ExtractFileDir(Application->ExeName); //Standart verzeichnis festlegen für den open & save Dialog! SaveDialog1->InitialDir = Pfad; OpenDialog1->InitialDir = Pfad; //Einstellung der Größe von Form1 (Karteikarte) Form1->Width = Panel1->Width + 18; Form1->Height = Panel1->Height + 15 + Button1->Height + 75; //Ermitteln der maximalen länge des Textes in den Edit Feldern E_Nachname->MaxLength =sizeof(myDat.Nachname)-2; E_Vorname->MaxLength =sizeof(myDat.Vorname)-2; E_Strasse->MaxLength =sizeof(myDat.Strasse)-2; E_NR->MaxLength =sizeof(myDat.Nr)-2; E_ORT->MaxLength =sizeof(myDat.Ort)-2; E_TEL->MaxLength =sizeof(myDat.Tel)-2; E_email->MaxLength =sizeof(myDat.email)-2; E_Geburtsdatum->MaxLength =sizeof(myDat.Geburtsdatum)-2; //Hint --> Angabe der Max. Breite der Felder E_Nachname->Hint="maximal" + IntToStr(sizeof(myDat.Nachname)-2) + "Zeichen"; E_Vorname->Hint="maximal" + IntToStr(sizeof(myDat.Nachname)-2) + "Zeichen"; E_Strasse->Hint="maximal" + IntToStr(sizeof(myDat.Nachname)-2) + "Zeichen"; E_NR->Hint="maximal" + IntToStr(sizeof(myDat.Nachname)-2) + "Zeichen"; E_ORT->Hint="maximal" + IntToStr(sizeof(myDat.Nachname)-2) + "Zeichen"; E_TEL->Hint="maximal" + IntToStr(sizeof(myDat.Nachname)-2) + "Zeichen"; E_email->Hint="maximal" + IntToStr(sizeof(myDat.Nachname)-2) + "Zeichen"; E_Geburtsdatum->Hint="maximal" + IntToStr(sizeof(myDat.Nachname)-2) + "Zeichen"; } //---------------------------------------------------------------------------Dummy Button --> Testwerte
void __fastcall TForm1::Button1Click(TObject *Sender) { //Dummy Werte übergeben in die Struktur! können nicht zugewiesen werden müssen kopiert werden strcpy(myDat.Nachname, "Müller"); strcpy(myDat.Vorname, "Manfred"); strcpy(myDat.Strasse, "Am Höllenschlund"); strcpy(myDat.Nr, "666a"); strcpy(myDat.Ort, "Hölle"); myDat.PLZ = 666; strcpy(myDat.Tel, "Devil-666"); strcpy(myDat.email, "Hölle@666.com"); strcpy(myDat.Geburtsdatum, "01.01.0001"); //int n=sizeof (myDat); //Werte in die Edit Felder ausgeben E_email->Text = myDat.email; E_Geburtsdatum->Text = myDat.Geburtsdatum; E_Nachname->Text = myDat.Nachname; E_Vorname->Text = myDat.Vorname; E_NR->Text = myDat.Nr; E_ORT->Text = myDat.Ort; E_PLZ->Text = IntToStr(myDat.PLZ); E_Strasse->Text = myDat.Strasse; E_TEL->Text = myDat.Tel; } //---------------------------------------------------------------------------Beenden
void __fastcall TForm1::Beenden1Click(TObject *Sender) { Form1->Close(); if (Dat_Open == true) { dat_io.close(); } }Neuen Datensatz erstellen
void __fastcall TForm1::Neu1Click(TObject *Sender) { if(SaveDialog1->Execute() == true) { DateiName = SaveDialog1->FileName; dat_io.open(DateiName.c_str(),ios::binary|ios::trunc); Dat_Open = true; } }Ausgefüllte Felder als Datensatz schreiben
void __fastcall TForm1::B_NeuClick(TObject *Sender) { //Textfelder auslesen & Datensatz zuweisen! strcpy(myDat.Nachname, E_Nachname->Text.c_str()); strcpy(myDat.Vorname, E_Vorname->Text.c_str()); strcpy(myDat.Strasse, E_Strasse->Text.c_str()); strcpy(myDat.Nr, E_NR->Text.c_str()); strcpy(myDat.Ort, E_ORT->Text.c_str()); myDat.PLZ =StrToInt(E_PLZ->Text); strcpy(myDat.Tel, E_TEL->Text.c_str()); strcpy(myDat.email, E_email->Text.c_str()); strcpy(myDat.Geburtsdatum,E_Geburtsdatum->Text.c_str()); //Datensatz an die Datei anhängen Anpassen der Größe dat_io.write((char*) & myDat, sizeof(myDat)); }So bis hier Funktioniert alles!
Speichern
void __fastcall TForm1::Speichern1Click(TObject *Sender) { if(SaveDialog1->Execute() == true) { DateiName = SaveDialog1->FileName; dat_io.open(DateiName.c_str(),ios::binary | ios::app); dat_io.write((char*) & myDat, sizeof(myDat)); Dat_Open = true; } }Laden:
void __fastcall TForm1::Laden1Click(TObject *Sender) { if(OpenDialog1->Execute() == true) { DateiName = OpenDialog1->FileName; dat_in.open(DateiName.c_str(),ios::failbit | ios::in | ios::binary | ios::app); if(dat_in.is_open()) { dat_in.get((char*)& myDat, sizeof (myDat)); //dat_in.read((char*)& myDat, sizeof(myDat)); //dat_in.read(DateiName.c_str(), sizeof(myDat)); //dat_in.get((char*)& myDat, sizeof (myDat)); //Werte in die Edit Felder ausgeben E_Nachname->Text = myDat.Nachname; E_Vorname->Text = myDat.Vorname; E_Strasse->Text = myDat.Strasse; E_NR->Text = myDat.Nr; E_ORT->Text = myDat.Ort; E_PLZ->Text = IntToStr(myDat.PLZ); E_TEL->Text = myDat.Tel; E_email->Text = myDat.email; E_Geburtsdatum->Text = myDat.Geburtsdatum; Dat_Open = true; DatensatzNR(); } } } //---------------------------------------------------------------------------Datensatzzahl:
void TForm1::DatensatzNR(void) { DateiName = OpenDialog1->FileName; dat_in.open(DateiName.c_str(),ios::in | ios::binary | ios::app); if(dat_in.is_open()) { //seekg sucht das Ende des Datensatzes dat_in.seekg (ifstream::beg,ifstream::end); //tellg --> gibt die Größe in Bytes an (Gesammtgröße des Datensatzes) int nBytes=dat_in.tellg(); //Ermitteln der Größe eines Datensatzes int nmyDat = sizeof (myDat); //die ermittelte Gesamtgröße geteilt durch die Datensatzgröße int n = nBytes / nmyDat; /*Datensatznummer in der Statusbar ausgeben*/ SB1->Panels->Items[1]->Text=IntToStr(n); } }Vielen dank für die Hilfe

-
Hallo
wenn du schon mit dem BCB arbeitest, warum nimmst du nicht einfach TStringList, um die Daten zu sammeln und in eine Datei zu schreiben/daraus zu laden? Das würde den Code sehr vereinfachen, und sicher auch den Fehler umgehen.
bis bald
akari
-
Hi, ja da hast du recht...
Jedoch beschäftige ich mich ja gerade mit Streams und wollte dies Progie so wie ichs gestaltet habe erstmal zuende bringen, einfach der Übung wegen!Denn ich will ja nicht vor dem Prob wegrennen sondern es bewältigen denn nur so lernt man ja Proggen ^^
hier bin mit dem Laden und zählen weitergekommen habe nen wenig weiter getüftelt... fertig ist's noch nicht... und fehlerfrei auch nicht aber die funktionen sind etwas mehr gegeben ^^
void TForm1::DatensatzNR(int Byte,int myDat) { //die ermittelte Gesamtgröße geteilt durch die Datensatzgröße int n = Byte/myDat; /*Datensatznummer in der Statusbar ausgeben*/ SB1->Panels->Items[1]->Text=IntToStr(n); }void __fastcall TForm1::Laden1Click(TObject *Sender) { if(OpenDialog1->Execute() == true) { DateiName = OpenDialog1->FileName; dat_in.open(DateiName.c_str(),ios::in | ios::binary); if(!dat_in.is_open()) { //Datei ist nicht offen! Application->MessageBox("Ihr Datensatz konnte nicht geöffnet werden.", "! FEHLER !", MB_OK); } else { //Werte in die Edit Felder ausgeben dat_in.read((char*)& myDat, sizeof(myDat)); E_Nachname->Text = myDat.Nachname; E_Vorname->Text = myDat.Vorname; E_Strasse->Text = myDat.Strasse; E_NR->Text = myDat.Nr; E_ORT->Text = myDat.Ort; E_PLZ->Text = IntToStr(myDat.PLZ); E_TEL->Text = myDat.Tel; E_email->Text = myDat.email; E_Geburtsdatum->Text = myDat.Geburtsdatum; Dat_Open = true; //seekg sucht das Ende des Datensatzes dat_in.seekg (ifstream::beg,ifstream::end); //nBytes --> tellg --> gibt die Größe in Bytes an (Gesammtgröße des Datensatzes) nBytes=dat_in.tellg(); //nmyDat --> Ermitteln der Größe eines Datensatzes nmyDat = sizeof (myDat); DatensatzNR(nBytes,nmyDat); } } } //---------------------------------------------------------------------------Danke dir aber für deine Antwort
-
Hallo
fertig ist's noch nicht... und fehlerfrei auch nicht
Hm... erwartest du jetzt eine Antwort? Wenn ja, erklär doch erstmal präzise den Fehler und was du wissen willst.
bis bald
akari
-
Hi @ akari
Also mein Problem liegt darin, das er die Strings alle ausgibt jedoch gibt er zuviel aus in den einzelnen Edit Feldern!
Versuche das mal andres zu erklären!
1.E_Feld --> Müller //Funktioniert
2.E_Feld --> Mannfred Am H //Gibt noch die strasse mit aus
usw.wie könnte ich die string in den Editfeldern begrenzen ?
Habe da nichts für gefunden habe das jetzt über "dat_in.get()" gelöst jedoch habe ich da mit dem "integer - Wert" Probleme der auch Binäre gespeichert wurde!Hier ist meine neue Ausgabe:
Die Lade Funktion:
//--------------------------------------------------------------------------- void __fastcall TForm1::Laden1Click(TObject *Sender) { if(dat_in.is_open()||dat_io.is_open()) { dat_io.close(); dat_in.close(); } if(OpenDialog1->Execute() == true) { DateiName = OpenDialog1->FileName; dat_in.open(DateiName.c_str(),ios::in | ios::binary); if(!dat_in.is_open()) { //Datei ist nicht offen! Application->MessageBox("Ihr Datensatz konnte nicht geöffnet werden.", "! FEHLER !", MB_OK); } else { //Datei offen //Daten-Werte in die Edit Felder ausgeben Ausgabe_Daten(); Dat_Open = true; //seekg sucht das Ende des Datensatzes dat_in.seekg (ifstream::beg,ifstream::end); //nBytes --> tellg --> gibt die Größe in Bytes an (Gesammtgröße des Datensatzes) nBytes=dat_in.tellg(); //nmyDat --> Ermitteln der Größe eines Datensatzes nmyDat = sizeof (myDat); DatensatzNR(nBytes,nmyDat); } } } //---------------------------------------------------------------------------Habe zwecks übersichtlichkeit eine neue Funktion erstellt!
void Ausgabe_Daten(void);
Hier://--------------------------------------------------------------------------- void TForm1::Ausgabe_Daten(void) { /* dat_in.read((char*)& myDat, sizeof(myDat)); E_Nachname->Text = myDat.Nachname; E_Vorname->Text = myDat.Vorname; E_Strasse->Text = myDat.Strasse; E_NR->Text = myDat.Nr; E_ORT->Text = myDat.Ort; E_PLZ->Text = IntToStr(myDat.PLZ); E_TEL->Text = myDat.Tel; E_email->Text = myDat.email; E_Geburtsdatum->Text = myDat.Geburtsdatum; */ char ch; AnsiString buff; int Postl; for(int i=0;i<=sizeof(myDat.Nachname)-1 ;i++) { dat_in.get(ch); buff = buff + ch; E_Nachname->Text = buff; } buff =""; for(int i=0;i<=sizeof(myDat.Vorname)-1;i++) { dat_in.get(ch); buff = buff + ch; E_Vorname->Text = buff; } buff =""; for(int i=0;i<=sizeof(myDat.Strasse)-1;i++) { dat_in.get(ch); buff = buff + ch; E_Strasse->Text = buff; } buff =""; for(int i=0;i<=sizeof(myDat.Nr)-1;i++) { dat_in.get(ch); buff = buff + ch; E_NR->Text = buff; } buff =""; for(int i=0;i<=sizeof(myDat.Ort);i++) { dat_in.get(ch); buff = buff + ch; E_ORT->Text = buff; } buff =""; for(int i=0;i<=sizeof(myDat.PLZ)+1;i++) { dat_in.get(ch); Postl = ch; buff = IntToStr(Postl); E_PLZ->Text = buff; } buff =""; for(int i=0;i<=sizeof(myDat.Tel)-1;i++) { dat_in.get(ch); buff = buff + ch; E_TEL->Text = buff; } buff =""; for(int i=0;i<=sizeof(myDat.email)-1;i++) { dat_in.get(ch); buff = buff + ch; E_email->Text = buff; } buff =""; for(int i=0;i<=sizeof(myDat.Geburtsdatum);i++) { dat_in.get(ch); buff = buff + ch; E_Geburtsdatum->Text = buff; } } //---------------------------------------------------------------------------So bei dieser Art & Weise funktioniert alles bis auf die als Integer abgespeicherte PLZ!
Mit der Speicher Funktion habe ich auch noch Probleme!
Und zwar, wenn ich ios::app verwende speichert er den Datensatz nicht ab.
Wenn ich es wie folgt verwende, speichert er in ab, jedoch nur einen Datensatz & auch nur blanko! also nen leeren Datensatz von 200 Byte ^^.
KP warum! (beim öffnen nen automatisches trunk?)//--------------------------------------------------------------------------- void __fastcall TForm1::Speichern1Click(TObject *Sender) { if(SaveDialog1->Execute() == true) { DateiName = SaveDialog1->FileName; dat_io.open(DateiName.c_str(),ios::binary); dat_io.write((char*) & myDat, sizeof(myDat)); Dat_Open = true; } } //---------------------------------------------------------------------------So beim Speichern & Laden komme ich nicht weiter voran... Wenn jemand bzw. du akari,(da ja bis dato noch niemand weiter geschrieben hat ;)) nen Tip hat wie ich evt. die erste Lösung Splitten kann oder, in der 2. Lösung vernünftig die PLZ ausgeben kann wäre ich sehr dankbar!

Die Datensatznummer funktioniert, werde mich jetzt mit dem Switschen beschäftigen (also vor, zurück, An den Anfang, An den Ende)
MFG
Dennis alias cyby
-
Hallo
ich denke du solltest dir einfach mal dieses Thema aus der C++ FAQ anschauen, um deine Stream-Operationen in Ordnung zu bringen. Es gibt dort ein Absachnitt "Das letzte Beispiel zeigt wie man Datensätze schreiben und lesen kann."
Und dann kannst du auch char[] direkt an AnsiString übergeben, das must du nicht char für char kopieren./Edit : und statt der char[] im Struct kannst du auch gleich besser std:string oder AnsiString verwenden.
bis bald
akari
-
Danke dir ziehe ich mir mal rein...
Nur denke ich steht das auch nicht mehr als in meinen Büchern ^^ so beim flüchtigen überfliegen ^^aber werde mir das jetzt mal in ruhe zu gemüte führen...
MFG
Dennis alias cyby
-
Hi stehen doch nen paar antworten drin die ich gesucht habe *g*
danke dir nochmal wenn ich weiter probs habe oder absolute verständnisprobs werde ich mich nochmal melden!thx
