10 ms·
Macro lists are a rather elegant solution IMO. You cannot add cases to the enum without also adding cases to the switch. #define CMD_LIST CMD(1) CMD(2) CMD(3
by jadengeller 10y ago
Macro lists are a rather elegant solution IMO. You cannot add cases to the enum without also adding cases to the switch.
#define CMD_LIST CMD(1) CMD(2) CMD(3) CMD(4)
#define STATUS_LIST STATUS(1) STATUS(2) STATUS(3)
enum {
#define CMD(x) CMD ## x = x - 1,
CMD_LIST
#undef CMD
END_CMD
};
enum {
#define STATUS(x) STATUS ## x = x + 9,
STATUS_LIST
#undef STATUS
END_STATUS
};
void process_message(int x)
{
switch (x) {
#define CMD(x) case CMD ## x:
CMD_LIST
#undef CMD
process_command_msg(x);
break;
#define STATUS(x) case STATUS ## x:
STATUS_LIST
#undef STATUS
process_status_msg(x);
break;
default:
report_error(x);
break;
}
}
It's unfortunate that it isn't possible to write a macro macro that expands to that gross def/undef boilerplate we use in the switch.
- evincarofautumn 10y agoYou can use an x-macro: // cmds.def X(1) X(2) X(3) X(4) #undef X // elsewhere.h enum { #define X(x) CMD##x = x - 1, #include "cmds.def" END_CMD }; Or a higher-order macro: #define CMD_LIST(X) X(1) X(2) X(3) X(4) enum { #define CMD(x) CMD##x = x - 1, CMD_LIST(CMD) #undef CMD END_CMD };