以下情况:
我有一些宏,用于将变量的补数及其原始值存储在结构中。对于另一个宏,我想检查原始值是否等于存储的补码值的补码。但是奇怪的是我没有得到我期望的结果。 简化操作,将导致以下情况:
#include <stdbool.h>
#include <stdint.h>
#define CHECKVAR(var__, compl__) ((var__^compl__)==-1);
int main()
{
uint8_t var;
uint8_t complementvar;
var=3;
complementvar=~var;
bool checkOK=CHECKVAR(var,complementvar); /*-> I expect that all bits are set and hereby it is equal to "-1", but instead i get "false" */
return 0;
}
我的期望是(例如,在32位系统上:
complementvar
之后的值为0xfffffffc
(在〜运算符引起的整数提升为int并将左值隐式转换为{{1 }}。complementvar
;
uint8
var: 0000 0000 0000 0000 0000 0000 0000 0011
complementvar: 1111 1111 1111 1111 1111 1111 1111 1100
的结果为true,但是我总是收到false,因为XOR操作的结果(对我来说很奇怪)是0x000000ff?我正在使用什么编译器?它是MSVC ++ 11,但实际上解决方案应尽可能独立于编译器。 由于我也必须具有可移植性,因此使用C编译器的结果会有所不同吗?
答案 0 :(得分:3)
补数运算后complementvar的值为
0xfffffffc
不。看一下代码:
uint8_t complementvar;
complementvar=~var;
~var
的计算结果为您期望的值,但是complementvar
的类型为uint8_t
,因此转换仅产生0xfc
。
在您的检查步骤中,它再次被提升为int
,但是由于uint8_t
是 unsigned 类型,因此此处没有符号扩展名,您只得到{{1 }}位。这说明了您通过异或(0
)获得的结果。