Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Why are anonymous structs (non typedef'd) useful in c?

Tags:

c

struct

I realized that whenever I typed

typedef struct {
//  ...
} foo;

there was an anonymous struct that was being typedef'd. I couldn't think of any way to pass an anonymous struct to a function, so it seemed pretty useless.
The only use I could think of was something in c++ like this:

struct {
    char* name;
    int   age;
} alice;

void print_info(auto v) {
    printf("name: %s age: %i", v.name, v.age);
}

int main() {
    alice.name = "Alice";
    alice.age  = 24;
    print_info(alice);
}

Despite the fact that c lacks any similar built in polymorphism, it also allows for anonymous structs.

Can anybody find a situation where this is useful?

like image 413
Ace shinigami Avatar asked Dec 04 '25 14:12

Ace shinigami


1 Answers

Such un-typedef'd anonymous structures have very limited uses, but not quite zero uses. Basically, they allow you to group some data together in a function or a single source file.

One consquence of that is that any such variables defined at file scope should be static because there isn't a proper declaration available for use in other files. Inside a single function, the variable can be automatic or static as desired; I suppose that if you had struct { … } *peculiar; then you could even manage dynamic allocation. However, if you like playing with fire and double-maintenance nightmares, you can actually have references in other source files to the original variable — you just shouldn't do it! So, it would be possible to have (but please do not do this!):

  • file1.c

    struct { char* name; int age; } alice;
    
  • file2.c

    extern struct { char* name; int age; } alice;
    

However, if you need the information shared between source files, create a header and give the structure type a name (either via a tag or a typedef or both).

(Why does this work? Think about what the compiler sees after preprocessing? It sees equivalent information in each TU, and will get it right if the definitions/declarations match. But it is much easier to ensure they match when you have a single header providing them.)

Assuming you aren't indulging in such dubious practices, then you're correct that there's no way to pass such variables around. So you might have a use for a structured variable with file scope but internal linkage that can be accessed by multiple functions in the source file. Such designs are far from unheard of, though they're often a bit dubious.

Note that if you have:

static struct {
    char* name;
    int   age;
} alice;

static struct {
    char* name;
    int   age;
} bob;

then alice and bob have different types (so you can't write bob = alice; or alice = bob;).

So, overall, such variables have limited use, but not zero use. It is seldom a good idea to use such variables, but if there is a good reason (which stands up to careful critical review, preferably by several people), then you can go ahead and use them. But you need to be really sure the cost of a structure tag is not acceptable. (I would add the structure tag at least, if only to document what it represents better.)

like image 134
Jonathan Leffler Avatar answered Dec 07 '25 04:12

Jonathan Leffler



Donate For Us

If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!