Seite 1 von 1

QStrings in QFile lesen und schreiben

Verfasst: 12. August 2009 12:41
von Apollinaris
Hallo,

ich habe eine Frage an euch. Ich möchte mehrere QStrings und mehrere Variablen speichern in einem QFile und anschließen auslesen können. Das soll in eine Klasse gekappselt sein die ich IniFile gennant habe. Die Nutzung der Klasse soll für ein Projekt sein, in dem meine Einstellungen gespeichert werden, die ich beim Start an meine GUI übergeben möchte und beim Lauf meiner Applikation auch verändert möchte:

Code: Alles auswählen

class IniFile
{
public:
    IniFile();
    void update();
    void read();

private:
    QFile *file;
    QString *str1;
    QString *str2;
    unsigned char zahl1;
    unsigned char zahl2;
    QDir *dir;
    QTextStream *out;
};
Wie ihr sehen könnt, habe ich vor zwei Methoden zu implemtieren.

Einmal die Methode read(). Hier möchte ich aus eine Datei meine QStrings und Variablen auslesen. Zu sehen ist nur wie ein QFile erzeugt wird:

Code: Alles auswählen

void IniFile::read()
{
    dir = new QDir();
    currentpath = new QString;
    *currentpath = dir->currentPath();

    *
    //Daten auslesen und Member besetzen
    *

    file = new QFile(*currentpath + "myIni.ini");
    file->open(QIODevice::ReadWrite );

}
Mein Ansatz war, erstmal nur die Variablen auszulesen über eine Struktur, dies klappte sehr gut. Hier mein Ansatz:

Code: Alles auswählen

char data[sizeof(myStruct)];
memcpy(&data, &myStruct, sizeof(myStruct));
Meine Frage ist, wie mache ich das am besten, wenn ich die QStrings hinzufüge, weil die Strings variable größen sind und nicht immer gleich groß. QT bietet sicherlich eine saubere Lösung für mein Problem, ich hab es nur noch nicht gefunden. Hier bitte ich euch um Hilfe.

Die zweite Methode, soll die Möglichkeit bieten die Einstellungen speichern zu können, um beim nächsten Start mit neuen Parameter arbeiten zu können.

Code: Alles auswählen

void IniFile::update( neue Parameter)
{
    *
    *
}
Würde mich sehr freuen, wenn ihr mir weiterhelfen könnt oder hoffe auf Anregungen. Vielleicht hat jemand soetwas schon implemetiert und kann mir eine bessere Lösung vorschlagen.

Danke
Gruss
Apollinaris

Ich benutze QT 4.5 (open source)

Verfasst: 12. August 2009 12:48
von Mani99
Was du suchst heißt QSettings!

Das hier macht genau das was du willst, und ist qt-out-of-the-box!

Verfasst: 12. August 2009 13:32
von RavenIV
Du willst doch bestimmt in eine ini-Datei speichern.

Dafür kannst Du dies verwenden:

Code: Alles auswählen

 QSettings settings("/home/petra/misc/myapp.ini",
                    QSettings::IniFormat);
Schau Dir mal die Hilfe (Qt Assistant) zu QSettings an.

Verfasst: 12. August 2009 13:38
von solarix
nebenbei... das da:

Code: Alles auswählen

class IniFile
{
public:
    IniFile(); 
zusammen mit dem:

Code: Alles auswählen

void IniFile::read()
{
    dir = new QDir();
    currentpath = new QString; 
ergibt wohl Memory-Leaks. Ohne Destruktor wirst du vermutlich den Speicher nicht mehr freigeben. Aber seien wir ehrlich: da brauchts weder Membervariabeln (lokale wuerden es auch tun) noch Pointer.... :roll:

Verfasst: 12. August 2009 14:38
von Apollinaris
Hallo Mani99 und RavenIV,

ich habe mir gerade den Qt Assistant angesehen und bin noch nicht ganz durchgestiegen, aber ich denke das wird mein Problem mit der ini-Datei lösen. Habe bisher eine ini-Datei erzeugt und paar Integer reingeschrieben, gleich werde ich versuchen einen QString zu speichern und die Parameter anschließend auszulesen.

Vielen dank für den Tipp es mit QSettings zu lösen.



Hallo solarix,

die Member Variablen wollte ich nur zum reinschreiben benutzen. Du hast sicherlich recht, dass es auch ohne geht bzw mit lokalen.

Was meinst du mit Memory-Leaks? Kenne diesen Ausdruck nicht. Meinst du den speicher anfordern und anschließend mit delete wieder freigeben oder wann entstehen Memory-Leaks?

Verfasst: 12. August 2009 16:13
von Mani99
Du brauchst dir nur das "basic usage" ansehen, da wird genau das erklärt wie du was speicherst! Und halt etwas abstrahieren solltest du auch können!

Verfasst: 12. August 2009 16:24
von franzf
Apollinaris hat geschrieben:Was meinst du mit Memory-Leaks? Kenne diesen Ausdruck nicht. Meinst du den speicher anfordern und anschließend mit delete wieder freigeben oder wann entstehen Memory-Leaks?
Schau mal in $Suchmaschine nach.
Im Prinzip genau das Gegenteil von deinem:

Code: Alles auswählen

Item* item;
item = new Item;
item = new Item; 
Das zuvor dynamisch erstellte Item ist nicht mehr erreichbar, und es wurde nicht mit delete gelöscht. Es schwirrt im Speicher rum, bis das Betriebssystem den Speicher nach Programmende wieder "aufräumt".
Wenn du ein mit new angelegtes Objekt nicht mehr brauchst, musst du es mit delete wieder freigeben:

Code: Alles auswählen

Item*item;
item = new Item;
delete Item; // OK, Speicher freigegeben.
Item = new Item;

Verfasst: 12. August 2009 18:55
von Apollinaris
Hallo franzf,

danke für die Erklärung von Memory-Leaks. Ich werde beim nachsten Mal, wenn ich mit Objekten arbeite, dran denken den Speicher wieder freizugeben.


Ich hab noch eine Frage zum Hauptthema. Ich möchte Datentypen wie unsigend char in meiner ini-Datei speichern. Klappt problemlos. Jetzt möchte ich die wieder auslesen. Hier mein Versuch:

Code: Alles auswählen

unsigned char interval;

QSettings settings(*currentpath + "/myapp.ini", QSettings::IniFormat);
interval = settings.value("interval").toChar();
Dies klappt nicht, weil es nur die Methode toChar(); gibt. Jetzt dachte ich mir, das ich das einfach umwandle/konvertiere:

Code: Alles auswählen

interval = (unsigned char) settings.value("interval").toChar();
Aber dies klappt leider nicht. In der Klasse QChar hab ich auch keine Methode gefunden.

Kennt jemand eine Lösung oder eine andere Variante auszulesen?

Verfasst: 12. August 2009 22:33
von Mani99
Hast du die doku dazu schon gelesen? Anscheinend nicht!

Code: Alles auswählen

QString interval = settings.value("interval", "0").value<QString>();

Verfasst: 13. August 2009 00:59
von Apollinaris
Ja richtig, vielen Dank.

Code: Alles auswählen

uchar interval;

interval = settings.value("interval", "0").value<uchar>();
Entschuldigt meine Fragen, aber wie ihr erkennen könnt, bin ich ein blutiger Anfänger.