Macro to stringify an enum

C

Chris

This is what I want to do, I have enum and I want to turn it into a
string using the number I've assigned to and concatenting a string to
the end of it or displaying some error string for invalid enums.

typedef enum
{
Enabled = 1,
Disabled = 2
} State;

#define State_String(x) (\
(x == Enabled) ? #x":Enabled" : \
(x == Disabled) ? #x":Disabled" : \
#x":Unknown")

int main()
{
int i;

i = Enabled;
printf("State: %s", State_String(i));
i = Disabled;
printf("State: %s", State_String(i));
i = Disabled + 1;
printf("State: %s", State_String(i));

return 0;
}

I want the output to look like
1:Enabled
2:Disabled
3:Unknown

But the output is
i:Enabled
i:Disabled
i:Unknown

Anybody know how I can do this in a macro?

Thanks,
Cristov
 
E

Eric Sosman

Chris said:
This is what I want to do, I have enum and I want to turn it into a
string using the number I've assigned to and concatenting a string to
the end of it or displaying some error string for invalid enums.

typedef enum
{
Enabled = 1,
Disabled = 2
} State;

#define State_String(x) (\
(x == Enabled) ? #x":Enabled" : \
(x == Disabled) ? #x":Disabled" : \
#x":Unknown")

int main()
{
int i;

i = Enabled;
printf("State: %s", State_String(i));
i = Disabled;
printf("State: %s", State_String(i));
i = Disabled + 1;
printf("State: %s", State_String(i));

return 0;
}

I want the output to look like
1:Enabled
2:Disabled
3:Unknown

But the output is
i:Enabled
i:Disabled
i:Unknown

Anybody know how I can do this in a macro?

It cannot be done by a macro that generates a string
literal, because the string literal's contents are fixed
at compile time. The variable `i' takes on different
values as the program progresses, and the string literal
cannot change to reflect the changes in `i'.

If you are willing to change your printf() format
the problem can be solved:

#define STATE(x) (\
((x) == Enabled ? "Enabled" : \
((x) == Disabled ? "Disabled" : \
? "Unknown")
...
printf ("State: %d:%s\n", i, STATE(i));

Why insist on a macro, though? Do you have a special
reason not to use an ordinary function?
 
S

Stephen L.

Chris said:
This is what I want to do, I have enum and I want to turn it into a
string using the number I've assigned to and concatenting a string to
the end of it or displaying some error string for invalid enums.

typedef enum
{
Enabled = 1,
Disabled = 2
} State;

#define State_String(x) (\
(x == Enabled) ? #x":Enabled" : \
(x == Disabled) ? #x":Disabled" : \
#x":Unknown")

int main()
{
int i;

i = Enabled;
printf("State: %s", State_String(i));
i = Disabled;
printf("State: %s", State_String(i));
i = Disabled + 1;
printf("State: %s", State_String(i));

return 0;
}

I want the output to look like
1:Enabled
2:Disabled
3:Unknown

But the output is
i:Enabled
i:Disabled
i:Unknown

Anybody know how I can do this in a macro?

Thanks,
Cristov

I don't think you can with a macro. Also, each
invocation of `State_String(x)' puts one copy
of the strings into the program (some compilers
may combine these, but there's no guarantee).

Will something like this do what you want (I
assume you only want to define the enum's names
only once)?

#include <stdio.h>
#include <stdlib.h>
#include <assert.h>

typedef enum
{
Unknown = 0,
Enabled = 1,
Disabled = 2
} State;

static const char * const states[] = { [Enabled] "Enabled",
[Disabled] "Disabled",
[Unknown] "Unknown" };

#define State_String(x) \
(x == Enabled || x == Disabled) ? states[ x ] : states[ Unknown
]

int
main()
{
State i;

i = Enabled;

printf("State: %d:%s\n", i, State_String(i));
i = Disabled;
printf("State: %d:%s\n", i, State_String(i));
i = Disabled + 1;
printf("State: %d:%s\n", i, State_String(i));


return 0;
}


-
Stephen
 
C

Chris

Eric Sosman said:
It cannot be done by a macro that generates a string
literal, because the string literal's contents are fixed
at compile time. The variable `i' takes on different
values as the program progresses, and the string literal
cannot change to reflect the changes in `i'.

If you are willing to change your printf() format
the problem can be solved:

#define STATE(x) (\
((x) == Enabled ? "Enabled" : \
((x) == Disabled ? "Disabled" : \
? "Unknown")
...
printf ("State: %d:%s\n", i, STATE(i));

Why insist on a macro, though? Do you have a special
reason not to use an ordinary function?

Yeah, this is what I ended up doing in the end. I just wanted to keep
the code simple and readable instead of adding another function and
function prototype and all that. Figured if there was a way to do it
all in a macro then that would be good. Changing the printf was the
best way to do it once I realized that it could not be done simply
another way.

Thanks,
Cristov
 

Ask a Question

Want to reply to this thread or ask your own question?

You'll need to choose a username for the site, which only take a couple of moments. After that, you can post your question and our members will help you out.

Ask a Question

Members online

No members online now.

Forum statistics

Threads
473,733
Messages
2,569,440
Members
44,831
Latest member
HealthSmartketoReviews

Latest Threads

Top