I have a C API that defines an enum like so:
typedef enum
{
C_ENUM_VALUE_NONE = 0,
C_ENUM_VALUE_APPLE = (1 << 0),
C_ENUM_VALUE_BANANA = (1 << 1),
C_ENUM_VALUE_COCONUT = (1 << 2),
// etc.
C_ENUM_VALUE_ANY = ~0
} CEnumType;
There is a method that uses the enum, defined as:
void do_something(CEnumType types);
In C, you can call something like:
do_something(C_ENUM_VALUE_APPLE | C_ENUM_VALUE_BANANA);
However, if you try to call it this way in C++ (Linux, g++ compiler), you get an error, invalid conversion from ‘int’ to ‘CEnumType’.
What is the correct way to use this C API from my C++ application?
You need to cast int
s to enums in C++, but you can hide the cast in a custom OR
operator:
CEnumType operator|(CEnumType lhs, CEnumType rhs) {
return (CEnumType) ((int)lhs| (int)rhs);
}
With this operator in place, you can write your original
do_something(C_ENUM_VALUE_APPLE | C_ENUM_VALUE_BANANA);
and it will compile and run without a problem.
C++ has stricter rules than C regarding enums. You'll need to cast the value to the enumeration type when calling:
do_something((CEnumType)(C_ENUM_VALUE_APPLE | C_ENUM_VALUE_BANANA));
Alternatively, you can writer a wrapper function that takes an int
to do the cast for you, if you want to avoid writing the cast every time you call it:
void do_something_wrapper(int types)
{
do_something((CEnumType)types);
}
...
do_something_wrapper(C_ENUM_VALUE_APPLE | C_ENUM_VALUE_BANANA);
Though I don't know if I want to see what you get when you cross an apple with a banana...
In the case of bitwise operations, the expression evaluates to a primitive type, i.e. int
, long
, etc. However, your function takes a non-primitive type (CEnumType
). The only way I know of to bypass this is to cast the expression. For example:
do_something((CEnumType) (C_ENUM_VALUE_APPLE | C_ENUM_VALUE_BANANA));
CEnumType A;
A = (CEnumType)(A | C_ENUM_VALUE_APPLE);
You can use it this way too.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With