Willkommen ~Gast!
Registrieren || Einloggen || Hilfe/FAQ || Staff
Probleme mit der Registrierung im Forum? Melde dich unter registerEin Bild.
Autor Beitrag
000
21.01.2008, 01:55
Pyro Phoenix



Nachdem ich einigermaßen davon überzeugt bin, die Grundlagen von C/C++ zu kennen,
möchte ich jetzt mein erstes 'seriöses' Projekt starten.

Ich möchte mir einen *.ini Parser schreiben. Das heißt: ich möchte Werte in eine
Textdatei schreiben, und diese dann von einem Parser auswerten und ggf. der
dazugehörigen Variable zuweisen. Das ganze möchte ich in ANSI C realisieren.

Mein Problem ist Folgendes:
Ich habe noch nie soeine Art von Projekt gestaltet / realisiert.
Wie fange ich am besten damit an? Was muss ich beachten?
Kurzum: Wie mache ich das am besten?

--

zum Seitenanfang zum Seitenende Profil || Suche
001
21.01.2008, 03:17
Master Pegasus



Mach dir erstmal nen Plan was dein Programm genau können soll und braucht, hier ist z.B. wichtig ob die Reihenfolge der Parameter in der ini wichtig sind (simpler Parser, geht dann z.B. über Zeilennummer), oder ob das alles kreuz und quer ist und der das trotzdem können soll.

Dann überlegst du dir was du für Funktionen brauchst, vielleicht eine die die ini zeilenweise in eine einfach verkettete Liste einliest, eine die die einzelnen Zeilen in "Parameter" und "Wert" aufspaltet, ...

Und wenn du dir das so einigermaßen überlegt hast, ist dann mal der Zeitpunkt gekommen zu Editor und Compiler zu greifen und Stück für Stück deine Funktionen zu realisieren.

--

Was immer auch geschieht: Nie sollt Ihr so tief sinken, von dem Kakao, durch den man Euch zieht, auch noch zu trinken! -- Erich Kästner

zum Seitenanfang zum Seitenende Profil || Suche
002
21.01.2008, 07:49
chriss



UML dürfte dir da auch helfen deine Gedanken geordnet zu „Papier“ zu bringen.

http://de.wikipedia.org/wiki/UML

--

zum Seitenanfang zum Seitenende Profil || Suche
003
21.01.2008, 13:01
Pyro Phoenix



Für UML müsste man aber einen groben Plan von dem haben, was man machen
will. Und den hab ich leider 'noch' nicht.

Aber Master Pegasus hat mir da schon einen guten Ansatz geliefert.

Der Parser soll:

* Reihenfolgen unabhängig sein.
* Die Einzelnen Parameter und Werte jeweils
päärchenweise in einen array ablegen.
* Kommentare tolerieren.

bisher is mir aber nix weiter eingefallen.

--

zum Seitenanfang zum Seitenende Profil || Suche
004
21.01.2008, 18:17
Kriz



1. Watt is'n .INI Datei?
2. Welche Struktur besitzt sie?
3. Wie kann ich diese Struktur im Rechner abbilden (Stichwort Datenstrukturen)?
4. Brauche ich einen vollständigen Parser oder reicht ein simples "Abtasten" der Dateistruktur?
5. Wie manage ich den Datei-IO (Sequenziell oder Random-Access), gepuffert oder "in einem Rutsch"?
6. Ist der Aufwand berechtigt, wo es doch zig (OSS) INI-Libraries für C/C++ gibt?

Zu 2.: Die Struktur dürfte ja mittlerweile bekannt sein: Kommentare, Gruppenblöcke, Key-Value Paare (die MSDN ist das sehr redselig). Also hast du es nur mit 3 Gebilden zu tun, die du erfassen und verarbeiten musst.

Zu 3.: Bei Key-Value Paaren empfehlen sich assoziative Container (die du dir in C sowieso selber zusammencoden mußt, außer du hast gerade eine Lib parat), speziell Sets (Mengen). Vorteil: Jeder Key ist einzigartig, was multiple Vorkommen verhindert (Ausnahme Multisets, was aber hier schwachsinnig wäre, da die meisten INIs einzigartige Keys verwenden).

Zu 4.: Hier reicht wohl eher ein "Abtasten", ein vollständiger Parser wäre wie mit Kanonen auf Spatzen geschossen. Ansonsten ist Lex/Yacc dein Freund (auch als Win-Edition erhältlich), wobei das schon etwas Knowhow erfordert.

Zu 5.: Beim Datei-IO würde ich bei INI-Dateien erstmal den gesamten Inhalt in einem Rutsch einlesen und sequenziell in einem char*-Array puffern. Hier wild in der Datei rumseeken ist imho nicht nötig, im Array dann bequem hin- und herspringen ist dann bequemer. Vorab mußt du natürlich den Puffer auch genügen groß anlegen, d.h. du mußt die Dateigröße in Bytes rausfinden. An dieser Stelle ist das Seeken natürlich sinnvoll, wenn man den entsprechenden Algorithmus in C kennt.

Zu 6.: Für Lernzwecke ok, ansonsten vergeudete Zeit :-)

PS: Viele Wege führen nach Rom!

--

K:R-I)Z++
"CSS ist cascading style sheets. Und nicht so'n Ranzspiel." - dp
In memory of Voice († 2005/03/30)

zum Seitenanfang zum Seitenende Profil || Suche
005
21.01.2008, 21:09
Pyro Phoenix



Zu 1.: Datt is'n .INI Datei ;P

Zu 2.: Quellcode:;Kommentar
[Sektion]
;Kommentar
Schlüssel=Wert
Zu 3.: Bitte genauer erklären: "assoziative Container", "Sets", "Multisets"

Zu 4.: "Abtasten"? Ich dache mir eher, das der Parser den gewünschten Wert auf Anfrage liefert.

Zu 5.: strtok () (in Verbindung mit einer mir Momentan nicht einfallenden Routine) sollte ein guter Verbündeter sein. :P
€dit: Um die einzelnen Werte etc. zu ermitteln.

Zu 6.: Selbermachen rockt am meißten ... :P

--


Dieser Beitrag wurde am 21.01.2008 um 21:15 von Pyro Phoenix bearbeitet.
zum Seitenanfang zum Seitenende Profil || Suche
006
21.01.2008, 22:28
Bluthund



3. Stichwort STL... Und das Wort assoziativ solltest du schon auflösen können wenn du sowas schreiben willst ;)

4. Ich nehme an mit "Abtasten" meinte Kriz, dass du den ganzen fiesen Kram wie Grammatiken und reguläre Sprachen etc außen vor lässt und deshalb um so lustige Sachen wie nen Kellerautomaten schreiben um die Semantik zu prüfen drumherum kommst. Also dass du einfach sukzessive durch deine Datei wanderst und fröhlich nach chars kuckst die eine besondere Bedeutung haben (Kommentarzeichen, Wertzuweisungszeichen) und entsprechende Aktionen daraus resultieren lässt.

5. Das war wohl eher in die Richtung seek & tell gedacht.

6. Eigentlich rockt wiederverwenden am meisten.
Wenn Autohersteller jedesmal das Rad erfinden müssten vorm Bau eines Autos, wären unsere Straße und die sich darauf bewegenden Gefährte wahrscheinlich noch Stand der 30er Jahre.
Aber zum Lernen nicht verkehrt wie Kriz schon richtig gesagt hatte.

--

The C language combines all the power of assembly language with all the ease-of-use of assembly language.
"humorig is n blödwort :>" by -CarniGGeLjumpR-

zum Seitenanfang zum Seitenende Profil || Suche
007
21.01.2008, 23:29
Pyro Phoenix



Hmm jetzt stellt sich mir die Frage:

Wie realisiere ich am besten einen assoziativen Container (ala Map) in C?

Zu 4.:

€dit: Ausgebessert.

€2:

Zu 5.:
Quellcode:int getc_count( const char * const path, size_t * const result )
{
  FILE * input = fopen( path, "rb" );
  size_t size = 0;
  int failed = 1;
  int error = 0;
  int overflow = 0;
  if( input )
  {
    int ch = getc( input );
    while( ch != EOF )
     {
       if( !++size )overflow = 1, ch = EOF;
      else ch = getc( input );
      }
    if( ferror( input ))error = 1;
    if( fclose( input )== 0 && !overflow && !error )failed = 0;
}
  *result = size;
  return failed;
}
Geht auch noch besser da C&P.

--


Dieser Beitrag wurde am 21.01.2008 um 23:57 von Pyro Phoenix bearbeitet.
zum Seitenanfang zum Seitenende Profil || Suche
008
22.01.2008, 00:27
Bluthund



4. mach da mal nen Struktogramm bzw wenigstens nen anständigen PAP draus. Das sieht ja unsagbar sch**ße aus ;) Vorallem deshalb weil es keinen klar definierbaren Einstiegspunkt in den Graph gibt.
GetKey würde ich vor "if '='" stellen; Grund: damit hast du den Token schon gelesen und musst nicht nochmal zurückspringen. Sollte er aus irgendnem Grund nicht verwendbar sein (kein passendes = oder Value) kannst du ihn im nachhinein immernoch ignorieren/verwerfen.
Außerdem ist Rekursion vielleicht nicht unbedingt die simpelste Implementation für dein Vorhaben.

5. Absolut unnötig. Wie Kriz schon sagte: "An dieser Stelle ist das Seeken natürlich sinnvoll, wenn man den entsprechenden Algorithmus in C kennt." -> http://www.cplusplus.com/reference/clibrary/cstdio/ftell.html

edit: zu deinem assoziativen Container:
Im simpelsten Fall einfach als struct aus zwei gewünschten Datentypen. Ist zwar dann auch im Sinne der Erweiterbarkeit absoluter Krampf, aber hey es ist C :). Also sowas hier:
Quellcode:typedef struct sAsso_s
{
    char Key[256]; // natürlich auch gern mit Pointern
    char Val[256]; // aber dann darfst du auch viel mit malloc und free hantieren =)
} sAsso_t;

sAsso_t SuperDollesArray[MAX_ENTRIES];

void foo( void )
{
    sAsso_t* OderHaltDynamisch = malloc( sizeof(sAsso_t)*NeededEntries );
}
Wesentlich eleganter wäre es natürlich dann noch das ganze in ne LinkedList bzw DoubleLL zu stopfen. Evtl auch nen Binärer Baum geordnet nach den Keys wenn die Suche schnell gehen soll. Wie schon erwähnt führen viele Wege nach Rom :)
Nen Array wäre halt der am schnellsten zu verwirklichende. Ob es allerdings auch der simpelste ist will ich hier nicht bewerten.

--

The C language combines all the power of assembly language with all the ease-of-use of assembly language.
"humorig is n blödwort :>" by -CarniGGeLjumpR-


Dieser Beitrag wurde am 22.01.2008 um 00:45 von Bluthund bearbeitet.
zum Seitenanfang zum Seitenende Profil || Suche
009
22.01.2008, 01:46
Pyro Phoenix



Zu 5.:

Quellcode:long sizeOfFile ( FILE *p_stream )
{
    long    lFileSize;
    fpos_t    fPosCur;

    fgetpos ( p_stream, &fPosCur );

    fseek ( p_stream, 0, SEEK_END );

    lFileSize = ftell ( p_stream );

    fsetpos ( p_stream, &fPosCur );

    return lFileSize;
};
Das war zu einfach ^^ Trotz deiner Hilfe :P

Wirst jetz sicher sagen: "rewind (); hätte auch gereicht."
Aber ich bin jetz mal von der möglichkeit ausgegangen, das der positions pointer != 0 sein kann.

€dit: Warum spackt der Linker rum, wenn ich die Funktionsdefinition aus einer *.h in
eine *.c datei auslagere? Änder ich die Erweiterung auf *.cpp is ruhe.

Zitat:
Linker schrieb:
main.obj : error LNK2001: Nichtaufgeloestes externes Symbol "long __cdecl sizeOfFile(struct _iobuf *)" (?sizeOfFile@@YAJPAU_iobuf@@@Z)
Debug/INI Parser.exe : fatal error LNK1120: 1 unaufgeloeste externe Verweise

--


Dieser Beitrag wurde am 22.01.2008 um 01:54 von Pyro Phoenix bearbeitet.
zum Seitenanfang zum Seitenende Profil || Suche
010
22.01.2008, 01:53
theDon



Linking conventions: C++ hat name mangling, C nicht.

--

\o tanz den naziprau! o/

And more than ever, I hope to never fall,
Where enough is not the same it was before

zum Seitenanfang zum Seitenende Profil || Suche
011
22.01.2008, 08:36
Bluthund



Ieeeeeh getpos und setpos... seek&tell in umgekehrter Reihenfolge hätten das auch getan ;)
Mal davon abgesehen haben Definitionen nichts in Headerdateien verloren.

--

The C language combines all the power of assembly language with all the ease-of-use of assembly language.
"humorig is n blödwort :>" by -CarniGGeLjumpR-

zum Seitenanfang zum Seitenende Profil || Suche
012
22.01.2008, 14:23
Pyro Phoenix



Was is mit 'getpos' und 'setpos' nich in Ordnung?

Quellcode:struct section
{
    char *sectionname;
    struct section *next;
    struct section *prev;
};

struct kev_value
{
    char *key;
    char *value;
    struct key_value *next;
    struct key_value *prev;
    struct section *member;
};
LinkedList?

--


Dieser Beitrag wurde am 22.01.2008 um 14:35 von Pyro Phoenix bearbeitet.
zum Seitenanfang zum Seitenende Profil || Suche
013
22.01.2008, 15:57
Bluthund



An getpos und setpos ist nix verkehrt. War nur meine persönliche Meinung... Denn im Prinzip sind diese Funktionen völlig überflüssig, weil man mit seek und tell genau diese Funktionalität und noch andere hat (wie zB das direkte Anspringen des Endes).

Das was du da gemacht (struct kev_value) hast entspricht in etwa den Nodes in einer doppelt verketteten Liste (Doubly-Linked List). Nur das du deinen Datentyp schon direkt in die Node hardcodet hast und ne LL in C für gewöhnlich nen void* auf das eigentliche Datum enthält.
Ne "richtige" LL hätte dann noch eine Struktur welche die Liste selbst repräsentiert und einen Pointer auf das erste (bei DoublyLLs macht auch ein zusätzlicher Pointer auf das letzte Sinn) und einen auf das aktuelle Element enthält, um sagen zu können ich bin eine Liste und das ist mein erstes, aktuelles und letztes Element.

Ganz dringend würde ich dir empfehlen mal ein bisschen zum Thema Datenstrukturen rum zuforschen. Denn wenigstens den Begriff verkettete Liste sollte man drauf haben. Auf Basis derer lassen sich nämlich auch wunderbar andere Sachen wie binäre Bäume und Stacks implementieren indem man einfach oben aufsetzt.

--

The C language combines all the power of assembly language with all the ease-of-use of assembly language.
"humorig is n blödwort :>" by -CarniGGeLjumpR-

zum Seitenanfang zum Seitenende Profil || Suche
014
22.01.2008, 16:45
Kriz



Lektüre: Sedgewick - Algorithmen in C - Addison Wesley

Imho würde ich sowas auch gleich in C++ erledigen, da spart man sich viel Arbeit.

--

K:R-I)Z++
"CSS ist cascading style sheets. Und nicht so'n Ranzspiel." - dp
In memory of Voice († 2005/03/30)

zum Seitenanfang zum Seitenende Profil || Suche
015
22.01.2008, 17:06
Pyro Phoenix



Grml ... hab mir mal den Wiki eintrag angeschaut.

Ich blick da ned durch.

http://de.wikipedia.org/wiki/Datenstruktur
http://de.wikipedia.org/wiki/Verkettete_Liste
http://de.wikipedia.org/wiki/Bin%C3%A4rer_Suchbaum

€dit:

Grml² ...
ISBN: 3-893193769
ist nichtmehr lieferbar.

--


Dieser Beitrag wurde am 22.01.2008 um 17:13 von Pyro Phoenix bearbeitet.
zum Seitenanfang zum Seitenende Profil || Suche
016
22.01.2008, 17:59
Bluthund



eBay rettet: Zwar nur noch ein Exemplar gefunden aber besser als garkeins (280192870619) :)
Ansonsten hilft dir bestimmt auch gern die örtliche Bibliothek.

Außerdem wie Kriz schon gesagt hat: Ganz klar C++ oder ne andere objektorientierte Sprache. Die Wartbarkeit und Lesbarkeit des Codes ist einfach um vieles besser. Allein schon deshalb weil die Datenstrukturen fest mit den darauf anwendbaren Methoden verknüpft sind und nicht nur irgendwie lose in einem Modul herumdümpeln.
In C hättest du Listenstruktur+Nodestruktur und einen riesen Haufen Funktionen (Liste aufbauen, löschen, Elemente eintragen, umordnen, zurückgeben, löschen, ...) und jede Funktion muss wissen auf welchem Objekt sie arbeiten soll (dh über nen Pointer). Das funktioniert zwar aber es sieht nicht nur hässlich aus, es ist auch noch beschissen zu schreiben (musste sowas in C als Teil eines Belegs im ersten Semester machen).
Wobei man in C++ wahrscheinlich eh auf std::list zurückgreifen würde.

Da bist du aber jetzt ordentlich von deinem ursprünglichen Problem weg ;)

--

The C language combines all the power of assembly language with all the ease-of-use of assembly language.
"humorig is n blödwort :>" by -CarniGGeLjumpR-


Dieser Beitrag wurde am 22.01.2008 um 18:02 von Bluthund bearbeitet.
zum Seitenanfang zum Seitenende Profil || Suche
017
22.01.2008, 18:38
Pyro Phoenix



http://www-dbs.informatik.uni-heidelberg.de/teaching/ws2004/info1/InfoIDataStructures.pdf

Seite 9 -> Letztes Kästchen. Jetz hab ich die Sache mit der LinkedList kapiert :P

Ah stimmt. Ebay rockt. Gleich mal drauf geboten.

€dit:

ANSI C aus dem Grund, da man mit den Grundlagen beginnen soll ... ^^
C++ kann jeder. ( Vorrausgesetzt, er will es auch können )

--


Dieser Beitrag wurde am 22.01.2008 um 18:48 von Pyro Phoenix bearbeitet.
zum Seitenanfang zum Seitenende Profil || Suche
018
22.01.2008, 19:40
Bluthund



Zitat:
Pyro Phoenix postete
C++ kann jeder. ( Vorrausgesetzt, er will es auch können )
Wage ich zu bezweifeln.
Jemand, der keine Kenntnis von C hat, wird auch mit C++ nichts vernünftiges auf die Beine stellen können. C ist ja doch mehr oder weniger eine Untermenge von C++. Nicht umsonst hat der erste Compiler als vorläufige Ausgabe C-Code erzeugt.
C++ ist wesentlich komplexer als C und kann schon aus diesem Grund nicht einfacher beherrschbar sein. Schon alleine die Ein/Ausgabe über Streams und vor allem das Denken das Streams Objekte sind ist für einen Anfänger imo total unverständlich. printf() ist da imho schon wesentlich besser für den Einstieg geeignet. Außer man fängt vielleicht sofort mit OOP an. Aber ich denke mal ein Großteil wenn nicht sogar alle fangen mit imperativer Programmierung an (BASIC, Pascal, C).
Desweiteren gibt es einen Unterschied zwischen können und können.
Klar kann jeder "Hello World!" auf die Konsole ausgeben oder vielleicht sogar über ne GUI-Bibliothek. Auch kriegt derjenige vielleicht noch nen Taschenrechner hin oder er wurstelt irgendwas am HL/HL2SDK rum. Wenn dann aber grundlegende Kenntnisse über Kapselung, Vererbung, Polymorphismus, usw fehlen schreibt er stinknormalen C-Code, denn dann sind Klassen nur schönere structs.

Nichtsdestotrotz solltest du dein Vorhaben wie schon geplant in C umsetzen wenn du das möchtest.
Der Vorschlag C++ für sowas zu nehmen rührt nur daher, dass man einfach solche Dinge wie Datenstrukturen dort viel logischer und in sich geschlossen aufbauen kann. Spätestens wenn du fertig bist und du weißt was OOP ist (und laut eigener Aussage beherrschst du die Grundlagen von C/C++ ja, siehe #000), wirst du sowas höchstwahrscheinlich das nächste Mal objektorientiert lösen. ;)

--

The C language combines all the power of assembly language with all the ease-of-use of assembly language.
"humorig is n blödwort :>" by -CarniGGeLjumpR-

zum Seitenanfang zum Seitenende Profil || Suche
019
22.01.2008, 22:05
Pyro Phoenix



Hmm. Gut ich hab nix gesagt ;)

Zu 5(#004).: Wieso eigentlich Puffern? Is denk ich mal nicht nötig da die
Datei von Anfang bis Ende eingelesen wird und die Daten auch gleich in einer
LinkedList verwertet werden -> addSection() bzw addTopic()

€dit: Faxen is. Muss ich ja so oder so Puffern. *narf*

Ist es angebracht die Funktion zum hinzufügen von "key value"
Paaren 'addTopic' zu nennen?

--


Dieser Beitrag wurde am 22.01.2008 um 22:11 von Pyro Phoenix bearbeitet.
zum Seitenanfang zum Seitenende Profil || Suche
020
23.01.2008, 00:20
hausi



Wieso nicht einfach das normale set-Interface dafür nehmen und die Methode put(key, value) nennen? Wenn in einer ini zwei mal dem selben Key etwas zugewiesen wird, wird ja das zweite genommen und nicht ein zweiter Eintrag gemacht -> add ist eigentlich nicht korrekt.
Edit: Oder nenn es einfach set_value, wenn du put nicht nehmen willst. Aber ich würde sonst ggf. einfach mal anfangen und bei Problemen wieder posten, sonst wirst du damit nie fertig...

--


Dieser Beitrag wurde am 23.01.2008 um 00:22 von hausi bearbeitet.
zum Seitenanfang zum Seitenende Profil || Suche
021
23.01.2008, 02:21
theDon



Funktional > *.

--

\o tanz den naziprau! o/

And more than ever, I hope to never fall,
Where enough is not the same it was before

zum Seitenanfang zum Seitenende Profil || Suche
022
23.01.2008, 13:59
caedes



Zitat:
theDon postete
Funktional > *.
jo, mach das in haskell - das ist die zukunft!

--

caedes

Deutschland rückt nach Einschätzung der Sicherheitsbehörden im Superwahljahr verstärkt ins Visier von Terroristen.

zum Seitenanfang zum Seitenende Profil || Suche
023
23.01.2008, 18:28
Pyro Phoenix



Zitat:
hausi postete
... Aber ich würde sonst ggf. einfach mal anfangen und bei Problemen wieder posten, sonst wirst du damit nie fertig...
Ich Arbeite ja schon die ganze Zeit daran. ;)

Zitat:
caedes postete
jo, mach das in haskell - das ist die zukunft!
Nah ! Jetz hab ich mit C angefangen. Und irgendwann hör ich mit C++ auf. Reicht fürs erste.
€dit: Naja vielleicht wärs noch ganz ratsam sich durch ASM zu quälen.

Quellcode:typedef struct section * s_node;
    typedef struct key_value * kv_node;

    typedef struct section
    {
        char    *sectionname;
        s_node    next;
        s_node    prev;
        kv_node    first;
        kv_node    last;
    };

    typedef struct kev_value
    {
        char    *key;
        char    *value;
        kv_node    next;
        kv_node    prev;
        s_node    member;
    };

    struct section *root;
    struct section *actv;
    struct section *prev;

    int addSection ( char *name );
Quellcode:addSection ( char *name )
{
    if ( root == NULL )
    {
        root = new section;
        actv = root;

        root->first = NULL;
        root->last = NULL;
        root->next = NULL;
        root->prev = NULL;
        root->sectionname = name;
    }
    else
    {
        prev = actv;
        actv = new section;

        prev->next = (s_node)actv;

        actv->first = NULL;
        actv->last = NULL;
        actv->next = NULL;
        actv->prev = (s_node)prev;
        actv->sectionname = name;
    }
};
So habe ich das Hinzufügen von Sektionen realisiert. Is das ok so?

€dit2: 3, 2, 1 ... meins

--


Dieser Beitrag wurde am 23.01.2008 um 23:17 von Pyro Phoenix bearbeitet.
zum Seitenanfang zum Seitenende Profil || Suche
024
25.01.2008, 13:04
Pyro Phoenix



Update:

Quellcode:getSection ( char *name )
{
    if ( root == NULL )
    {
        root = (section *)malloc ( sizeof( section ) );        // Neues Sektions-Objekt bereitstellen.

        actvs = root;                                        // Aktive Sektion = root

        root->first            = NULL;
        root->last            = NULL;
        root->next            = NULL;
        root->prev            = NULL;
        root->sectionname    = name;                            // Name zuweisen.

        prevs = actvs;                                        // Fertig. Vorherige Sektion = Aktive Sektion.

        return 0;
    }
    else
    {
        actvs = (section *)malloc ( sizeof( section ) );    // Neues Sektions-Objekt bereitstellen.

        prevs->next            = actvs;                        // Neue Sektion mit der vorherigen Sektion verlinken.

        actvs->first        = NULL;
        actvs->last            = NULL;
        actvs->next            = NULL;
        actvs->prev            = prevs;                        // Vorherige Sektion in der neuen Sektion verlinken.
        actvs->sectionname    = name;                            // Name zuweisen.

        prevs = actvs;                                        // Fertig. Vorherige Sektion = aktive Sektion.

        return 0;
    }

    return 1;
};
Quellcode:getTopic ( char *key, char *value )
{
    if ( actvs->first == NULL )
    {
        actvkv = (key_value *)malloc ( sizeof( struct key_value ) );    // Neues Key-Value-Objekt bereitstellen.

        actvs->first = actvkv;                                            // Erstes Key-Value-Objekt mit aktiver Sektion verlinken

        actvkv->member    = actvs;                                        // KV-Objekt ist Member der aktiven Sektion.
        actvkv->key        = key;
        actvkv->value    = value;
        actvkv->prev    = NULL;
        actvkv->next    = NULL;

        prevkv = actvkv;                                                // Fertig. Vorheriges KV-Objekt = aktives KV-Objekt.

        return 0;
    }
    else
    {
        actvkv = (key_value *)malloc ( sizeof( struct key_value ) );    // Neues KV-Objekt bereitstellen.

        prevkv->next = actvkv;                                            // Aktives KV-Objekt im vorherigen verlinken.

        actvkv->member    = actvs;                                        // KV-Objekt ist Member der aktiven Sektion.
        actvkv->key        = key;
        actvkv->value    = value;
        actvkv->prev    = prevkv;                                        // Vorheriges KV-Objekt im aktuellen verlinken.
        actvkv->next    = NULL;

        prevkv = actvkv;                                                // Fertig. Vorheriges KV-Objekt = aktives KV-Objekt.

        return 0;
    }

    return 1;
};
Funktioniert 1A ... Jetzt wag ich mich mal an den Parser selbst.

--

zum Seitenanfang zum Seitenende Profil || Suche