使用枚举作为常量时 c 编译器的意外行为
unexpected behaviour of c compiler when using enumerate as constant
在下面的 C 代码中,函数 func1
决定枚举 ENUM1
的哪个元素作为输入。
在第一次调用中 func1(ENUM_ELEMENT1);
它按预期工作,但在第二次和第三次调用中结果是错误的(预计该函数分别打印 ENUM_ELEMENT2
和 ENUM_ELEMENT3
但是在这两种情况下,它都会打印 ENUM_ELEMENT1
)!
#include <stdio.h>
#include <stdint.h>
typedef enum
{
ENUM_ELEMENT1 = 0x0000001u,
ENUM_ELEMENT2 = 0x0000002u,
ENUM_ELEMENT3 = 0x0000004u,
ENUM_ELEMENT4 = 0x0000008u,
} ENUM1;
void func1( uint32_t inp )
{
if (0u != inp & ENUM_ELEMENT1)
{
printf("ENUM_ELEMENT1\n");
}
else if (0u != inp & ENUM_ELEMENT2)
{
printf("ENUM_ELEMENT2\n");
}
else if (0u != inp & ENUM_ELEMENT3)
{
printf("ENUM_ELEMENT3\n");
}
else if (0u != inp & ENUM_ELEMENT4)
{
printf("ENUM_ELEMENT4\n");
}
}
int main( void )
{
func1(ENUM_ELEMENT1); // prints ENUM_ELEMENT1 --> correct
func1(ENUM_ELEMENT2); // prints ENUM_ELEMENT1 --> wrong!
func1(ENUM_ELEMENT3); // prints ENUM_ELEMENT1 --> wrong!
getchar();
return 0;
}
这是operator precedence的事情。
表达式 0u != inp & ENUM_ELEMENT1
等于 (0u != inp) & ENUM_ELEMENT1
。如果 inp
非零,则 0u != inp
为真,可转换为整数 1
,而 1 & 1
确实为 "true".
在下面的 C 代码中,函数 func1
决定枚举 ENUM1
的哪个元素作为输入。
在第一次调用中 func1(ENUM_ELEMENT1);
它按预期工作,但在第二次和第三次调用中结果是错误的(预计该函数分别打印 ENUM_ELEMENT2
和 ENUM_ELEMENT3
但是在这两种情况下,它都会打印 ENUM_ELEMENT1
)!
#include <stdio.h>
#include <stdint.h>
typedef enum
{
ENUM_ELEMENT1 = 0x0000001u,
ENUM_ELEMENT2 = 0x0000002u,
ENUM_ELEMENT3 = 0x0000004u,
ENUM_ELEMENT4 = 0x0000008u,
} ENUM1;
void func1( uint32_t inp )
{
if (0u != inp & ENUM_ELEMENT1)
{
printf("ENUM_ELEMENT1\n");
}
else if (0u != inp & ENUM_ELEMENT2)
{
printf("ENUM_ELEMENT2\n");
}
else if (0u != inp & ENUM_ELEMENT3)
{
printf("ENUM_ELEMENT3\n");
}
else if (0u != inp & ENUM_ELEMENT4)
{
printf("ENUM_ELEMENT4\n");
}
}
int main( void )
{
func1(ENUM_ELEMENT1); // prints ENUM_ELEMENT1 --> correct
func1(ENUM_ELEMENT2); // prints ENUM_ELEMENT1 --> wrong!
func1(ENUM_ELEMENT3); // prints ENUM_ELEMENT1 --> wrong!
getchar();
return 0;
}
这是operator precedence的事情。
表达式 0u != inp & ENUM_ELEMENT1
等于 (0u != inp) & ENUM_ELEMENT1
。如果 inp
非零,则 0u != inp
为真,可转换为整数 1
,而 1 & 1
确实为 "true".