Results 1 to 7 of 7

Thread: struct comparison

Hybrid View

  1. #1

    Thread Starter
    Lively Member
    Join Date
    Mar 2002
    Location
    The Netherlands
    Posts
    64

    struct comparison

    How can you check two structs in C in a if statement if they are the same without going threw all the items of the struct seperately?
    the == statement doesn't work

    thanx in advance

  2. #2
    Monday Morning Lunatic parksie's Avatar
    Join Date
    Mar 2000
    Location
    Mashin' on the motorway
    Posts
    8,169
    You could do a memcmp:
    Code:
    #include <stdio.h>
    
    typedef struct {
        int x;
        char *str;
        double num;
    } thing_t;
    
    int main(void) {
        thing_t first = { 5, "Hello!", 1.2 };
        thing_t second = { 5, "Hello!", 1.2 };
        
        if(!memcmp(&first, &second, sizeof(thing_t))) {
            printf("Structures are identical\n");
        } else {
            printf("Structures are different\n");
        }
        
        return 0;
    }
    Note that we now have an intriguing problem. On my system, it says they're identical. This is because it's noticed the two "Hello!" strings are the same, and folded them into the same pointer. This means that the memory comparison determines they're equal.

    Those two strings could be the same, but have *different* pointer values. In this case, the structures would be different, but what they *meant* would be the same.

    How you want them to be compared is up to you. If they're simple (i.e., just numbers, no pointers) then you can get away with memcmp(). I would suggest having a specific compare function for anything else:
    Code:
    #include <stdio.h>
    #include <assert.h>
    #include <float.h>
    #include <math.h>
    
    struct thing_t {
        int x;
        char *str;
        double num;
    };
    
    int compare_things(const struct thing_t* first, const struct thing_t* second) {
        assert(first != NULL && second != NULL);
        
        return (first->x == second->x && !strcmp(first->str, second->str) && fabs(first->num - second->num) <= DBL_EPSILON);
    }
    
    int main(void) {
        struct thing_t first = { 5, "", 1.2 };
        struct thing_t second = { 5, "", 1.2 };
        
        char a[] = "Hello";
        char b[] = "Hello";
        
        first.str = a;
        second.str = b;
        
        if(a == b) {
            printf("Strings are the same array...shouldn't be!\n");
        } else {
            printf("Good, strings are different\n");
        }
        
        printf("\n");
        
        if(compare_things(&first, &second)) {
            printf("Structures are identical\n");
        } else {
            printf("Structures are different\n");
        }
        
        return 0;
    }
    Note that I've also added a specific check for the floating-point numbers to try and avoid rounding errors. I'm not convinced about that, so I'll let someone else make any comments if they wants to.
    I refuse to tie my hands behind my back and hear somebody say "Bend Over, Boy, Because You Have It Coming To You".
    -- Linus Torvalds

  3. #3
    Kitten CornedBee's Avatar
    Join Date
    Aug 2001
    Location
    In a microchip!
    Posts
    11,594
    I always thought that == would automatically compare memberwise...

    In C++ you can of course overload the == operator, in C you'll have to go with parksie's approach.
    All the buzzt
    CornedBee

    "Writing specifications is like writing a novel. Writing code is like writing poetry."
    - Anonymous, published by Raymond Chen

    Don't PM me with your problems, I scan most of the forums daily. If you do PM me, I will not answer your question.

  4. #4
    Monday Morning Lunatic parksie's Avatar
    Join Date
    Mar 2000
    Location
    Mashin' on the motorway
    Posts
    8,169
    Code:
    [mike@relativity junk]$ gcc -o structs structs.c 
    structs.c: In function `main':
    structs.c:42: invalid operands to binary ==
    I refuse to tie my hands behind my back and hear somebody say "Bend Over, Boy, Because You Have It Coming To You".
    -- Linus Torvalds

  5. #5
    Frenzied Member
    Join Date
    Jul 2002
    Posts
    1,370
    Somehow I'm not getting memcmp above:

    memcmp returns 0 when equal.

    memcmp will compare two separate memory locations and work
    correctly. In most C implementations it is what is behind strcmp().

    It doesn't have anything to do with memory locations or different datatypes. If the bytes at the two addresses match you get a zero return.

  6. #6
    Kitten CornedBee's Avatar
    Join Date
    Aug 2001
    Location
    In a microchip!
    Posts
    11,594
    Which part confuses you then?
    All the buzzt
    CornedBee

    "Writing specifications is like writing a novel. Writing code is like writing poetry."
    - Anonymous, published by Raymond Chen

    Don't PM me with your problems, I scan most of the forums daily. If you do PM me, I will not answer your question.

  7. #7
    Monday Morning Lunatic parksie's Avatar
    Join Date
    Mar 2000
    Location
    Mashin' on the motorway
    Posts
    8,169
    What I was trying to demonstrate is that even if memcmp decides they're different, they may actually mean the same (i.e. have the same string data, but a different pointer).
    I refuse to tie my hands behind my back and hear somebody say "Bend Over, Boy, Because You Have It Coming To You".
    -- Linus Torvalds

Posting Permissions

  • You may not post new threads
  • You may not post replies
  • You may not post attachments
  • You may not edit your posts
  •  



Click Here to Expand Forum to Full Width