Есть ли способ в стандартном C - или с расширениями GNU - добавить что-то в определение макроса? Например, , учитывая макрос, определенный как
#define List foo bar
, могу ли я добавить bas
, чтобы он List
расширялся, как если бы я определил его
#define List foo bar bas
?
Я надеялся, что смогу сделать что-то вроде этого:
#define List foo bar bas
#define List_ Expand(List)
#undef List
#define List Expand(List_) quux
, но я не могу понять, как определить Expand ()
макрос, чтобы он делал то, что я хочу.
Мотивация: Я играю с размеченными / помеченными союзами в следующих направлениях:
struct quux_foo { int x; };
struct quux_bar { char *s; };
struct quux_bas { void *p; };
enum quux_type {quux_foo, quux_bar, quux_bas};
struct quux {
enum quux_type type;
union {
struct quux_foo foo;
struct quux_bar bar;
struct quux_bas bas;
} t;
};
Я считаю, что это хорошее место для X-макроса. Если я определю макрос
#define quux_table X (foo) X (bar) X (bas)
, перечисление и структура могут быть определены таким образом, и они никогда не рассинхронизируются:
#define X(t) quux_ ## t,
enum quux_type {quux_table};
#undef X
#define X(t) struct quux_ ## t t;
struct quux {
enum quux_type type;
union {quux_table} t;
};
#undef X
Конечно, quux _ *
структуры могут рассинхронизироваться, поэтому я хотел бы сделать что-то вроде этого, только законно:
struct quux_foo { int x; };
#define quux_table quux_table X(foo)
struct quux_bar { char *s; };
#define quux_table quux_table X(bar)
struct quux_bas { void *p; };
#define quux_table quux_table X(bas)
(Ну, я действительно хочу иметь возможность делать это что-то вроде
member_struct (quux, foo) {int x;};
но я хорошо знаю, что макросы нельзя (пере) определять из макросов.)
В любом случае, это мой мотивирующий пример. Есть ли способ добиться этого?
Примеры Boost.Preprocessor подойдут, если вы можете показать мне, как заставить X-macro работать с этой библиотекой.