Reputation: 1574
I'm trying to manually implement a polymorphic behavior in C by creating a generic struct, and then derived structs (if you will) which can be told apart by the value of an enum, so that I can have a pointer to the generic type, dereference it as the generic type, figure out what type it is, and then dereference it as the more specific type.
typedef struct{
enum type structType;
//... other stuff all the structs share
}generic;
typedef struct{
generic; //does not work, obviously, nor does (generic){};
//... other stuff unique to struct type A
}typeA;
I understand that I could just declare a named instance of the generic struct in the derived struct, but this seems a little messy, and I would prefer not to if there's a neat and tidy way around it.
Upvotes: 4
Views: 297
Reputation: 33601
You can't always get what you want, but if you try sometimes, well, you might find, you get what you need ...
There are two basic ways, with a slight bit of trickery:
generic.h
GENERIC
I've used both methods at various times.
Here's the method with the include file (generic.h
):
enum type structType;
int com_fd;
void *com_buf;
And, here's a .c
file that uses it:
typedef struct {
#include <generic.h>
} generic;
typedef struct {
#include <generic.h>
// other stuff unique to struct type A ...
int typea_value;
} typeA;
Here's the method using a macro:
#define GENERIC \
enum type structType; \
int com_fd; \
void *com_buf
typedef struct {
GENERIC;
} generic;
typedef struct {
GENERIC;
// other stuff unique to struct type A ...
int typea_value;
} typeA;
Upvotes: 2
Reputation: 153457
Can you declare an anonymous instance of a named struct?
No.
Yet code can make-up a name based on the line number, to keep it unique and with some level of animosity.
Now code should not try to reference var.member11
as the member's name changes as the code for typeA
definition moves about in the file.
#define ANON_1(A,B) A##B
#define ANON_2(A,B) ANON_1(A,B)
#define ANON ANON_2(member, __LINE__)
typedef struct{
int x;
} generic;
typedef struct{
generic ANON; // name will be something like: member10
generic ANON; // name will be something like: member11
int y;
} typeA;
int main() {
typeA var;
(void) var;
return 0;
}
I suspect though to achieve OP's higher goal, a better approach is possible.
Upvotes: 0