In C, the following code would not compile:
enum Foo{
A
};
enum Bar{
A
};
because in C, enums don’t introduce a new namescope and thus a name clash happens if you use the same identifier A
for both types Foo
and Bar
.
Cython would translate (if it would just apply its usual scheme and not stop with a compiler-error):
#foo.pyx
cpdef enum Fruit:
UNKNOWN = 0
cpdef enum Animal:
UNKNOWN = 0
to something like
enum __pyx_t_3foo_Fruit {
__pyx_e_3foo_UNKNOWN = 0
};
enum __pyx_t_3foo_Animal {
__pyx_e_3foo_UNKNOWN = 0
};
and as we have seen, this is not valid C, so Cython's choice is to generate an error. A "problem" is that Cython doesn't include the type name (Fruit
, Animal
) into the generated enum-value-name, so while in Cython you would be able to differentiate between them as Fruit.UNKNOWN
and Animal.UNKNOWN
, they would map to the same C-identifier.
There are at least two options:
A: The usual strategy in C is to use a prefix to differentiate between the enums, e.g.:
cpdef enum Fruit:
FRUIT_UNKNOWN = 0
cpdef enum Animal:
ANIMAL_UNKNOWN = 1
or B: you can let Cython to do this work by putting them in different pxd-files, which are imported in the resulting pyx-file:
# Fruit.pxd
cpdef enum Fruit:
UNKNOWN = 0
#Animal.pxd
cpdef enum Animal:
UNKNOWN = 0
# foo.pyx:
cimport Fruit
cimport Animal
# use Fruit.UNKNOWN and Animal.UNKNOWN
in the resulting code, the enum-names will have the module names (i.e. Fruit
and Animal
) and thus are not the same from C-compiler's point of view.