Problem mit Stack - Verwaltung von Wörtern mit Hilfe von Pointern



  • Hallo, ich habe Probleme bei meinem Stack.
    Ich will meinen Stack als Array implementieren, der Zeiger auf Wörter von variabler Länge hält.
    Die Struktur sieht folgendermaßen aus:

    #define STACKSIZE       10
    
    struct Stack
    {
    	char *elements[STACKSIZE];
    	int size;
    };
    

    So nun Frage 1: Habe ich das richtig gemacht, dass der Stack nun ein Array von 10 Zeigern auf char-Arrays von variabler Länge hält?

    Dann weiter im Code:
    global:

    struct Stack gStack;
    

    Teil von main():

    struct Stack *stPtr;
    stPtr = &gStack;
    char *zeichen;
    printf("\npush:\t");
    scanf("%200s", &zeichen);
    

    Zur zweiten Frage:
    Ist es richtig, dass ich hier die Wortlaenge auf 200 Zeichen beschraenke?

    push(stPtr, zeichen);                    
    if(stPtr->size < STACKSIZE-1)              
       top = stPtr->elements[(stPtr->size)-1];
    

    Funktion push:

    void push(struct Stack *ptr, char *str)
    {
        if (!isFull())
        {
            char *tmp;
            tmp = malloc(sizeof(*str));
            if (tmp != NULL)
            ptr->elements[ptr->size++] = tmp;
        }
    	else
    	{
    	    printf("\nStack ist voll! Fuehren Sie pop() aus.\n\n");
    	}
    }
    

    Das Problem ist, dass ich nur kryptische Zeichenfolgen auf meinem Stack liegen habe, wahrscheinlich ist es eine Referezierungs/Dereferenzierungs-Geschichte, da verliere ich noch recht häufig den Überblick ob jetzt * oder & kommen muss.

    Hier nochmal die Funktion, mit der ich mir den ganzen Stack printe zum Prüfen:

    printStack(stPtr);
    
    void printStack (struct Stack *ptr)
    {
        char *tmp = ptr->elements[0];
        int i;
        printf("\n\n####################################\n");
        for (i=0;i<ptr->size;i++)
        {
            printf("\ngStack.elements[%d]: %s\n", i, tmp);
            tmp++;
        }
        printf("\n####################################\n\n");
    }
    

    Ich hoffe ich hab alles gut durchstrukturiert und nichts vergessen, damit mir schnell geholfen werden kann.

    Danke schonmal fürs Lesen,
    Gruß Tomi.



  • @1) Ja, das ist ein Array mit zehn char-Zeigern. Ob das für deinen Bedarf ausreicht, mußt du wissen.

    @2) Wie groß ist denn der Speicherbereich, den du für zeichen bereitgestellt hast? Davon hängt es ab, wieviel Platz du zur Verfügung hast für die Eingabe.

    Ansonsten: du reservierst in der push()-Funktion eindeutig zu wenig Speicher, um die Eingaben schlucken zu können - da hast du Glück, daß du "nur" kryptische Ausgaben erhalten hast.


  • Mod

    Zu Frage 1:
    Ja, das sind 10 Zeiger auf char-Arrays.

    Zu Frage 2:
    Nein, es werden maximal 200 Zeichen gelesen, aber dann wird noch eine Nullterminierung dran gehängt, der Buffer muss 201 Zeichen groß sein.

    Zum Problem:
    sizeof(*str) ist 1. *str ist nämlich ein einzelnes Zeichen. Wenn du die Länge von Zeichenketten bestimmen willst, nimm strlen.
    Mag sein, dass noch mehr Fehler drin sind, diesen habe ich jedoch sofort im Verdacht gehabt bei der Fehlerbeschreibung und habe dann nicht weiter gesucht, als ich diesen Fehler dann auch gefunden habe.



  • #define STACKSIZE       10
    
    typedef struct {
        int size;
        char *elements[STACKSIZE];
    } Stack;
    
    int push(Stack *stack,const char *s)
    {
      if( stack->size==(sizeof stack->elements/sizeof*stack->elements) ) return 0;
      strcpy(stack->elements[stack->size++]=malloc(strlen(s)+1),s);
      return 1;
    }
    
    char *pop(Stack *stack)
    {
      if( !stack->size ) return 0;
      return stack->elements[--stack->size];
    }
    
    void print(const Stack *stack)
    {
      int i=stack->size;
      while( i-- )
        puts(stack->elements[i]);
    }
    
    int main()
    {
      Stack stack={0};
      push(&stack,"1");
      push(&stack,"2");
      print(&stack);
      puts(pop(&stack));
      print(&stack);
      /* Speicherfreigabe der Werte aus pop sowie elements fehlt noch */
      return 0;
    }
    


  • Wutz schrieb:

    strcpy(stack->elements[stack->size++]=malloc(strlen(s)),s);
    

    Fehlt in der Zeile nicht noch ein "+1"?



  • Ah ok, das wusste ich nicht, dass das mit dem sizeof nicht klappt..
    Habs jetzt soweit abgeaendert aber irgendein Speicherzugriffsproblem bekomme ich noch, wenn ich push ausfuehren will.

    int push(Stack *ptr, const char *str)
    {
        if (!isFull())
        {
            strcpy(ptr->elements[ptr->size++]=malloc(strlen(str)+1),str);
    
            return 1;
        }
    	else
    	{
    	    printf("\nStack ist voll! Fuehren Sie pop() aus.\n\n");
    	    return 0;
    	}
    }
    


  • Woher weiß die isFull()-Funktion eigentlich, mit welchem Stack sie arbeiten soll?

    Ansonsten: Debugger



  • Hm ja, ich werd mir das Ganze nochmal genauer angucken.

    isFull sieht folgendermaßen aus:

    bool isFull()
    {
        if (gStack.size == STACKSIZE)
            return true;
        else
            return false;
    }
    

    Werd ich dann am Ende anpassen, dass nen Pointer auf den Stack uebergeben wird, aber wollte das bisher erstmal so lassen.

    malloc(strlen(str)+1)
    

    Das +1 mach ich doch nur, weil strlen das \0 nicht mitberechnet oder?

    Edit: es scheint irgendwie an strlen zu liegen.



  • Dein isFull verwendet globale Variablen sowie C++ Datentypen.
    Entscheide dich mal, was du überhaupt willst, mit globalen Variablen oder lokalen als Funktionsparameter arbeiten, bzw. mit C oder C++.
    Bisher ist dein Code alles nur Stümperei ohne klare Linie.


Anmelden zum Antworten