Menu

Earn Premium with Referrals

Invite your friends and earn Premium rewards through our referral program.

See how it works and start inviting friends.

Comparison Questions - Part 2
C

Comparison Questions - Part 2

Solve 15 challenging C comparison questions involving structs, enums, pointers, and tricky unsigned comparisons.

16. What does this enum comparison print?

#include <stdio.h>

enum color { RED, GREEN, BLUE };

int main(void) {
    enum color c = GREEN;

    printf("%d\n", c == 1);
    printf("%d\n", c < BLUE);
    printf("%d\n", RED < GREEN);
    return 0;
}

Output:

1
1
1

Enum constants are integers, assigned 0, 1, 2 by default. So GREEN is 1 and c == 1 is 1. c < BLUE is 1 < 21, and RED < GREEN is 0 < 11. Enums compare exactly like their underlying integer values.

17. What does this struct comparison attempt print?

#include <stdio.h>
#include <string.h>

typedef struct {
    int x;
    int y;
} Point;

int main(void) {
    Point p1 = {1, 2};
    Point p2 = {1, 2};

    printf("%d\n", memcmp(&p1, &p2, sizeof(Point)) == 0);
    return 0;
}

Output:

1

You cannot use == on structs in C — it is a compile error. The standard way to compare is memcmp(&p1, &p2, sizeof(Point)), which compares the raw bytes. Since both structs hold identical fields and there is no padding gap here, memcmp returns 0 and the comparison is 1. (Padding bytes can make memcmp unreliable — comparing fields individually is safer.)

18. What does this integer-promotion comparison print?

#include <stdio.h>

int main(void) {
    char c = 'A';

    printf("%d\n", c == 65);
    printf("%d\n", c < 'a');
    printf("%d\n", sizeof(c) < sizeof(int));
    return 0;
}

Output:

1
1
1

char promotes to int in comparisons, so c == 65 ('A') is 1. 'A' < 'a' is 65 < 971. And sizeof(char) < sizeof(int) is 1 < 41. Character comparison always goes through integer promotion.

19. What does this precedence comparison print?

#include <stdio.h>

int main(void) {
    int x = 5;

    printf("%d\n", x == 5 == 1);
    printf("%d\n", x == 5 == 0);
    printf("%d\n", (x == 5) == 0);
    return 0;
}

Output:

1
0
0

x == 5 == 1 parses as (x == 5) == 1 = 1 == 11 (left-associative). x == 5 == 0 is 1 == 00. (x == 5) == 0 is 1 == 00. Comparisons of comparisons are legal but almost always a bug — the inner comparison is a 0/1 value that you then compare again.

20. What does this <= on unsigned wrap print?

#include <stdio.h>

int main(void) {
    unsigned int i;

    for (i = 5; i <= 4; i--)
        printf("loop\n");
    printf("done %u\n", i);

    return 0;
}

Output:

done 5

The loop condition i <= 4 is false immediately (5 <= 4), so the body never runs. Because the condition fails at entry, neither the body nor the iteration expression i-- executes — i stays 5. This is the trap with decrementing loops: if the initial value already fails the condition, no wrap-around happens. (Change the condition to i > 4 — always true for unsigned — and the loop would spin forever, which is the classic infinite-unsigned-loop bug.)

21. What does this pointer-not-equal loop print?

#include <stdio.h>

int main(void) {
    int arr[] = {10, 20, 30};
    int *p = arr;
    int *end = arr + 3;

    while (p != end) {
        printf("%d ", *p);
        p++;
    }
    printf("\n");
    return 0;
}

Output:

10 20 30 

The while (p != end) idiom walks the array until the pointer reaches one-past-the-last element. Each iteration prints the current element and advances p. p != end becomes false exactly after printing 30. Comparing pointers with != (not <) is the classic iteration pattern.

22. What does this switch-on-comparison print?

#include <stdio.h>

int main(void) {
    int score = 85;

    switch (score >= 60) {
        case 1:
            printf("pass\n");
            break;
        case 0:
            printf("fail\n");
            break;
    }
    return 0;
}

Output:

pass

score >= 60 evaluates to the int 1 (true). switch compares that against the case labels 1 and 0, matching case 1 — printing "pass". This works because comparisons produce 0/1 ints, which switch labels can match directly.

23. What does this == on unsigned max print?

#include <stdio.h>

int main(void) {
    unsigned int u = 0;
    u = u - 1;

    printf("%u\n", u);
    printf("%d\n", u == 4294967295u);
    printf("%d\n", u == -1);
    return 0;
}

Output:

4294967295
1
1

u = u - 1 wraps from 0 to 4294967295 (the unsigned max). u == 4294967295u is 1. And u == -1 is also 1: the -1 is converted to unsigned for the comparison, becoming 4294967295. Both comparisons print 1 — the “unsigned -1” equivalence is a classic gotcha.

24. What does this strcmp equal-string comparison print?

#include <stdio.h>
#include <string.h>

int main(void) {
    char s[10] = "abc";
    char t[10] = "abc";
    char u[10] = "abd";

    printf("%d\n", strcmp(s, t));
    printf("%d\n", strcmp(s, t) == 0);
    printf("%d\n", strcmp(s, u) < 0);
    return 0;
}

Output:

0
1
1

strcmp returns 0 for equal strings, so strcmp(s, t) prints 0 and strcmp(s, t) == 0 is 1. "abc" < "abd" lexicographically, so strcmp(s, u) < 0 is 1. Remember: strcmp == 0 means equal — beginners often wrongly test strcmp(s, t) directly in a condition.

25. What does this negated comparison print?

#include <stdio.h>

int main(void) {
    int a = 3, b = 5;

    printf("%d\n", a != b);
    printf("%d\n", !(a == b));
    printf("%d\n", a < b != 0);
    return 0;
}

Output:

1
1
1

a != b is 1 (they differ). !(a == b) is !(0)1. a < b != 0 parses as (a < b) != 0 = 1 != 01. All three print 1, illustrating the equivalence of x != y and !(x == y).

26. What does this constant-comparison print?

#include <stdio.h>

int main(void) {
    printf("%d\n", '0' == 0);
    printf("%d\n", '0' == 48);
    printf("%d\n", '\0' == 0);
    printf("%d\n", '\n' == 10);
    return 0;
}

Output:

0
1
1
1

'0' is the character digit zero, ASCII 48, not the numeric 0 — so '0' == 0 is 0 and '0' == 48 is 1. '\0' is the null character, ASCII 0, so '\0' == 0 is 1. '\n' is ASCII 10, so '\n' == 10 is 1. Confusing '0' with 0 is a classic C bug.

27. What does this value-vs-pointer comparison print?

#include <stdio.h>

int main(void) {
    int x = 10;
    int *p = &x;

    printf("%d\n", *p == x);
    printf("%d\n", p == &x);
    printf("%d\n", *p == 10);
    printf("%d\n", &*p == &x);
    return 0;
}

Output:

1
1
1
1

*p is the value at the address, so *p == x is 1 and *p == 10 is 1. p == &x compares addresses, which match — 1. And &*p cancels out to &x1. All four print 1; the first two compare values, the last two compare addresses.

28. What does this two’s-complement comparison print?

#include <stdio.h>

int main(void) {
    int x = -2;

    printf("%d\n", x < 0);
    printf("%d\n", x == ~1);
    printf("%d\n", x == -2);
    return 0;
}

Output:

1
1
1

x = -2 is negative, so x < 0 is 1. ~1 is the bitwise NOT of 1 — in two’s complement, ~1 is -2, so x == ~1 is 1. And x == -2 is trivially 1. This tests the relationship between ~ and negative numbers: ~n == -(n+1).

29. What does this decrement-comparison loop print?

#include <stdio.h>

int main(void) {
    int i = 3;

    while (i--)
        printf("%d ", i);
    printf("\n");

    i = 3;
    while (--i)
        printf("%d ", i);
    printf("\n");
    return 0;
}

Output:

2 1 0 
2 1 

First loop: i-- tests the old value (3, truthy) then decrements, so the body prints 2, 1, 0 — the loop stops when the tested value is 0. Second loop: --i decrements first then tests, so the body prints 2, 1 — when i becomes 0 the condition is false and 0 is never printed. Post-decrement in the condition includes printing 0; pre-decrement does not.

30. What does this array-bounds comparison print?

#include <stdio.h>

int main(void) {
    int arr[4] = {1, 2, 3, 4};
    int i;

    for (i = 0; i <= 3; i++)
        printf("%d ", arr[i]);
    printf("\n");

    for (i = 0; i < sizeof(arr) / sizeof(arr[0]); i++)
        printf("%d ", arr[i]);
    printf("\n");
    return 0;
}

Output:

1 2 3 4 
1 2 3 4 

Both loops iterate all four elements. i <= 3 works because the highest valid index is 3. The second loop computes the element count with sizeof(arr) / sizeof(arr[0]) — the canonical portable way to get an array’s length. Comparing i < count (not <=) avoids an off-by-one into out-of-bounds. Using <= with a hardcoded bound is the classic overflow source.

My Private Notes

Notes are auto-saved locally to this device.