Search code examples
cpointersfor-loopinfinite-loop

Infinite Loop when using 'for' with pointer as loop variable


I am quite new to coding and got stuck with a problem. I tried to solve it myself and have been googling a lot, but I still do not have a solution to this. Maybe one of you can help?

This is my code:

int main(int argc, char **argv) {
    struct node {
        char *str;
        int count;
        struct node *next;
    };

    struct node head = { argv[1], 1, NULL };
    for (int i = 2; i < (argc); i++) {
        for (struct node *p = &head; (p != NULL); p = p->next) {
            printf("%s,%s\n", argv[i], p->str);
            if (strcmp(argv[i], p->str) == 0) {
                printf("case1\n");
                p->count++;
                break;
            }
            else if ((strcmp(argv[i], p->str) != 0) && p->next) {
                printf("case2\n");
                printf("Adresse, auf die p zeigt: %p", &p);
                continue;
            }
            else if ((strcmp(argv[i], p->str) != 0) && (!p->next)) {
                printf("case3\n");
                struct node *oldhead = &head;
                head.str = argv[i];
                head.count = 1;
                head.next = oldhead;
                break;
            }

        }
    }

    // Print how many times each string appears

    return 0;
}

The goal is to create a linked list that contains all the arguments I gave to the main() when calling the program. If there is a duplicate, the structure should count them. For example, if i call the program like ./a.out foo fool foo the result should be a list of length two, where the first element contains the string "foo" and count 2, and the second element contains the string "fool" and has a count of 1. The problem is the else if-statement within the inner for loop. This is the only part where the inner for loop should actually be used and assign p->next to p. Unfortunately that is not happening. The result is that the inner for loop starts over and over again and the pointer p points to the same address all the time (I used printf to figure that out).

Does any of you have an idea what could be the problem here? I tried everything I could and tried to find a solution online ...

Thanks a lot!!!


Solution

  • The issue is in this part of the code

       else if ((strcmp(argv[i], p->str) != 0) && (!p->next)) {
            printf("case3\n");
            struct node *oldhead = &head;
            head.str = argv[i];
            head.count = 1;
            head.next = oldhead;
            break;
        }
    

    You need to allocate a new struct and then put its address in the last struct entry.

           else if ((strcmp(argv[i], p->str) != 0) && (!p->next)) {
                printf("case3\n");
                struct node *oldhead = p;
                p = (struct node *) malloc(sizeof(node));
                if (p == NULL) { .... manage the error ... }
                oldhead->next = p;
                p->str = argv[i];
                p->count = 1;
                p->next = NULL;
                break;
            }
    

    Now you're creating nodes and stringing them together. You were effectively updating the same node before.