Einfach verkettete Liste / Malloc



  • Hey:)
    wo ist mein Denkfehler? 😞 Bin C Neuling!
    Aufgabe..: Datentyp mit Funktionen zur Verwaltung von Personen werden implementiert .Die Daten werden in einer einfach verketteten linearen Liste verwaltet, wobei die
    Listenelemente im Heap - Speicherbereich liegen.

    Schreiben eine Funktion append, die beim Aufruf Name und Alter und einen Zeiger (p)
    auf das erste Listenelement erhält und ein neues Listenelement mit den übergebenen Daten
    als letztes Listenelement einfügt. p kann auch den Wert NULL haben. Als Ergebnis wird ein
    Zeiger auf den Listenanfang zurückgeliefert.
    -------------------------------------------------------------

    #include <stdio.h>
    #include <stdlib.h>
    
    typedef struct person {
    	char name[20];  //Datenbereich
    	int age;//Daten
    	struct pers *next; //Zeiger auf den Nachfolger
    }	person; //Name des structs
    
    int main ()
    {
    	append( (? was kommt hier rein?) , "Peter",21);  //Aufruf richtig?
    
    }
    
    person append ( person *p, char *name, int age )    
    { 	
    
    	p = (person *)malloc(sizeof(person));
    	p->name[20]=*name;
    	p->age=age;
    	p->next;
    	return *p;
    
    }
    

    //Steh gerade auf dem Schlauch und wäre um jede EINFACHE Erklärung SEHR dankbar! 😕 Schreibe bald eine Klausur und daher ist das echt mehr als wichtig!

    Vielen vielen Dank im voraus!
    MFG
    Peter



  • Whereeaglesdare schrieb:

    #include <stdio.h>
    #include <stdlib.h>
    
    typedef struct person {
    	char name[20];  //Datenbereich
    	int age;//Daten
    	struct pers *next; //Zeiger auf den Nachfolger
    }	person; //Name des structs // könnte man auch person_list oder so nennen
    
    int main ()
    {
    	append( (? was kommt hier rein?) , "Peter",21);  //Aufruf richtig? // Erster Parameter sollte vielleicht 0 sein?
    
    }
    
    person /* Du willst eher einen Pointer zurückgben. */ append ( person *p, char *name, int age ) // const char*
    { 	
    	p = (person *)malloc(sizeof(person)); // Erst mal p auf 0 testen? // (Und void* muss in C nicht gecastet werden, aber das würde ich hier mal als nicht so wichtig ansehen.)
    	p->name[20]=*name; // strncpy! So kann man keine Strings kopieren
    	p->age=age;
    	p->next; // Was genau soll das bewirken?
    	return *p; // ..
    	
    }
    

    Normalerweise setzt du das letzte ->next auf 0, so dass du darüber das Ende indentifizieren kannst. Wenn dann etwas angehängt werden soll, gehst du über die ganze Liste bis ->next == 0 ist. Dann hängst du ein neues Element dran.



  • Bevor man dynamische Speicherverwaltung benutzt, solte man erstmal die Grundlagen von C beherschen.

    Mach erstmal die Funktion append richtig.



  • Wie schon erwähnt, hast du wenig Ahnung von den C Grundlagen, eigne sie dir erstmal an (Zeiger/Array, string, struct/typedef, ... ) bevor du mit verketteten Listen rummachst.
    Und lies die Compilerwarnungen. Der Compiler hat immer recht!
    Und übersetze C Code immer mit einem C Compiler und nicht mit einem C++ Compiler.

    #include <stdio.h>
    #include <string.h>
    #include <stdlib.h>
    #include <assert.h>
    
    typedef struct person {
        char name[30];
        int age;
        struct person *next; /* hier muss natürlich auch struct person stehen und nicht struct pers wie vorher */
    }    Person; /* Name des (neuen) Typs, nicht Name des struct */
    
    Person *append ( Person *p, char *name, int age )
    {
      Person **x=&p;
      while( *x ) /* bis zu dem Element laufen, an dem next==NULL ist, bei p==NULL bricht Schleife sofort ab */
        x=&(*x)->next;
    
      /* hier ist x ein ZEIGER auf einen ZEIGER auf das neu anzuhängende Element, *x ist hier ==NULL */
      assert(!*x);
    
      *x = calloc(1,sizeof**x); /* Speicher für neues anzuhängendes Element reservieren und (implizit) next=NULL setzen */
      strcpy((*x)->name,name);
      (*x)->age=age;
    
      return p;
    }
    
    int Ausgabe ( const Person *anfang ) /* Liste durchhecheln und Elementinhalt ausgeben, dies wäre ein Testfall für deinen, d.h. meinen Code */
    {
      int r=0;
      while( anfang )
        printf("%s %d\n",anfang->name,anfang->age),anfang=anfang->next,r++;
      return r;
    }
    
    int main ()
    {
      Person *anfang=0;  /* Zeiger auf Anfang der Liste; hier noch NULL, da noch keine Liste vorhanden */
    
      anfang = append( anfang , "Dr.plag.", 40);
      anfang = append( anfang , "Karl-Theodor", 40);
      anfang = append( anfang , "Maria", 40);
      anfang = append( anfang , "Nikolaus", 40);
      anfang = append( anfang , "Johann", 40);
      anfang = append( anfang , "Jacob", 40);
      anfang = append( anfang , "Philipp", 40);
      anfang = append( anfang , "Franz", 40);
      anfang = append( anfang , "Joseph", 40);
      anfang = append( anfang , "Sylvester", 40);
      anfang = append( anfang , "Freiherr", 40);
      anfang = append( anfang , "von und zu Guttenberg", 40);
    
      assert( 12==Ausgabe( anfang ) ); /* Testfall, liegt immer in DEINEM eigenen Interesse! */
      return 0;
    }
    


  • @Wutz hast ein const vergessen bei append().


Anmelden zum Antworten