cdata-structureslinked-liststack

Why does calling two functions in a single statement not affect the value?


In this code:

// Stack using LinkedList //

#include <stdio.h>
#include <stdlib.h>

struct Node {
    int data;
    struct Node* next;
};

struct Node* top = NULL;

short isEmpty(void) {
    if (top == NULL) {
        printf("error: The stack is empty.\n");
        return 1;
    }
    
    return 0;
}

void push(int value) {
    struct Node* newNode = (void*)malloc(sizeof(struct Node));
    if (!newNode) {
        printf("error: Heap overflow!\n");
        exit(1);
    }
    
    newNode->data = value;
    newNode->next = top;
    top = newNode;
}

int pop(void) {
    if (isEmpty()) {
        exit(1);
    }
    
    struct Node* ref = top;
    int val = top->data;
    top = top->next;
    free(ref);
    
    return val;
}

int peek(void) {
    if (isEmpty()) {
        exit(1);
    }
    
    return top->data;
}

void display(void) {
    if (isEmpty()) {
        exit(1);
    }
    
    while (top) {
        printf("%d\n", top->data);
        top = top->next;
    }
}

int main(void) {
    push(10);
    push(20);
    push(30);
    push(40);
    
    printf("Peek: %d\n", peek());
    int val = pop();
    printf("Popped: %d, now Peek: %d\n", val, peek());
    push(50);
    display();
    
    return 0;
}

Have a look at these lines:

int val = pop();
printf("Popped: %d, now Peek: %d\n", val, peek());

It returns: Popped: 40, now Peek: 30

as expected. However, when writing it this way:

printf("Popped: %d, now Peek: %d\n", pop(), peek());

It yields this output: Popped: 40, now Peek: 40

Here's a Godbolt.

Can somebody enlighten me as to why it is that way?


Solution

  • The order of evaluation of function arguments is unspecified. So when you do this:

    printf("Popped: %d, now Peek: %d\n", pop(), peek());
    

    Either pop or peek could be called first.

    In your particular case, peek was apparently called first which returned the value 40 without removing the value from the stack, then the pop call removes that value from the stack and returns it, so 40 is printed both times.