Reputation: 16724
Assuming that I have this:
enum { A = 0x2E, B = 0x23, C = 0x40 }
it's possible check if x
is defined into enum
?
I'm doing it manually: int isdef = (x == A || x == B || x == C);
But I want to something more dynamic. GCC-extensions
are welcome too.
Upvotes: 14
Views: 48865
Reputation: 33
Here is another possible solution:
#include <stdio.h>
#include <stdint.h>
typedef enum {
VALUE_1 = 0x01,
VALUE_2 = 0x03,
VALUE_3 = 0x0A
} values_e;
int main(void)
{
int a = 0;
values_e vlr;
for (int i = 0; i < 10; i++) {
scanf("%d", &a);
vlr = (values_e)a;
switch (vlr) {
case VALUE_1:
printf("do ... value 1:\r\n");
break;
case VALUE_2:
printf("do ... value 2:\r\n");
break;
case VALUE_3:
printf("do ... value 3:\r\n");
break;
default:
printf("ops...\r\n");
}
}
}
Upvotes: 1
Reputation: 1
As already pointed out, it is not possible to check if an enum is defined by directly referring to an enum member. However, there is a very simple shortcut: define a unique identifier associated with each enumerated type. Then, when you want to check if an element of the enumeration exists, you can simply check if the associated identifier is defined:
//Header File:
typedef enum
{
ENUM_ELEMENT_1 = 0,
ENUM_ELEMENT_2 = 1,
ENUM_ELEMENT_3 = 2,
ENUM_ELEMENT_MAX
} eEnumElement;
#define ENUM_ELEMENT_DEFINED 1
...
//Source file:
void TaskOperateOnEnums(void)
{
#if defined(ENUM_ELEMENT_DEFINED)
eEnumElement Test = ENUM_ELEMENT_1;
...
#endif
}
Upvotes: 0
Reputation: 111
The easiest way to do this is:
enum {
MODE_A,
MODE_B,
MODE_C
};
int modeValid(int mode)
{
int valid = 0;
switch(mode) {
case MODE_A:
case MODE_B:
case MODE_C:
valid = 1;
};
return valid;
}
void setMode(int mode)
{
if (modeValid(mode)) {
// Blah, blah
}
}
int main(void)
{
setMode(1); // Okay
setMode(500); // Error
}
Upvotes: 11
Reputation: 30210
This is kind of a modified version of your question, but depending on what you're doing, something like this might work:
enum {A,B,C};
const int E[] = {0x2E,0x23,0x40};
// Or:
// enum { A = 0x2E, B = 0x23, C = 0x40 };
// const int E[] = {A,B,C};
int isEnum(int x)
{
for(int i=0; i<(sizeof(E)/sizeof(*E)); i++)
{
if(E[i] == x){ return 1; }
}
return 0;
}
int main(void)
{
printf("Value of A: 0x%02x\n", E[A]);
// Or:
// printf("Value of A: 0x%02x\n", A);
printf("isEnum(0x2e): %s\n", isEnum(0x2e) ? "true" : "false");
printf("isEnum(0x2f): %s\n", isEnum(0x2f) ? "true" : "false");
}
which outputs
Value of A: 0x2e isEnum(0x2e): true isEnum(0x2f): false
EDIT: TJD beat me to it, and his suggestion of using a sorted array and doing binary search would decrease your search time from n to log(n).
Upvotes: 13
Reputation: 2470
To expand on the accepted answer, use X-macros to build your enum and array from the same data using the preprocessor.
/* Only need to define values here. */
#define ENUM_VALUES \
X(A, 0x2E) \
X(B, 0x23) \
X(C, 0x40)
/* Preprocessor builds enum for you */
#define X(a, b) a = b,
enum {
ENUM_VALUES
};
#undef X
/* Preprocessor builds array for you */
#define X(a, b) a,
const int E[] = {
ENUM_VALUES
};
#undef X
/* Copied from accepted answer */
int isEnum(int x)
{
for(int i=0; i<sizeof(E);i++)
{
if(E[i] == x){ return 1; }
}
return 0;
}
Upvotes: 8
Reputation: 45057
An enum
is essentially the same thing as using macros to define constants, except that the enum
wraps a set of associated constants up into a data type. This makes your code more self-documenting, but doesn't really provide any additional functionality.
If you venture outside the realm of standard C, some compilers can do extra things with enum
that they can't do with macros. Some debuggers will map enum
variables back to their name instead of showing their value. Also, some compilers provide the ability to add run-time checks for things like out-of-bounds enum
values. This is essentially the same as the code you show, only the compiler adds it automatically. With GreenHills' C compiler, this feature is enabled with the -check=assignbound
compiler option. I'm not sure if gcc has something like this built-in or not. What compiler are you using?
Upvotes: 1
Reputation: 61351
Not to the best of my knowledge. An enum in C is just a cleaner alternative to a series of
#define A 0x2E
statements.
If the enum is large and its values happen to be continuous, declare min/max constants and compare to those:
enum { E_MIN = 0x2E, A = 0x2E, B = 0x23, C = 0x40 ..., E_MAX=0x100};
if(x >= MIN && x <= MAX)
ItsInEnum();
Upvotes: 13