首页 > 解决方案 > 为什么 C/C++ 按位 XOR 运算符关心符号?

问题描述

很长一段时间以来,我一直在为一些低级消息而苦苦挣扎,结果证明这是校验和计算的问题。我认为按位异或运算符不关心符号,所以我使用 aQByteArray来存储字节,并使用at返回 a 的方法char来计算校验和。有时会正确确认消息,但并非总是如此。

看起来另一端的人正在使用uint8_t存储字节,并且在某些情况下校验和失败。我通过投射charto解决了这个问题uint8_t,但我对此感到非常困惑。

为什么按位异或运算符关心符号?我认为它在位级别上起作用,无论它们代表什么。这是我用来尝试理解它的一段代码。

#include <stdio.h>
#include <stdint.h>
#include <iostream>
#include <bitset>

int main ()
{    
    uint8_t a = 0b10010101;
    char b    = 0b10010101;

    uint32_t checksum;

    checksum = 55;
    checksum ^= a;
    std::cout << std::bitset<32>(checksum) << std::endl;

    checksum = 55;
    checksum ^= b;
    std::cout << std::bitset<32>(checksum) << std::endl;    
}

即使两个整数持有相同的位,该操作在每种情况下都会产生不同的结果。

标签: c++bit-manipulationbitwise-operatorsbitwise-or

解决方案


首先,您必须记住,它char是有符号还是无符号的实现定义。

然后你必须记住,在表达式中使用较小类型的值时,比如or被提升为(char可能) 。此促销带来了已签名类型的符号扩展uint8_tintunsigned int

因此,如果char有符号,则该值0b10010101将被提升为0b11111111111111111111111110010101(对负数使用二进制补码)。这与无符号值非常不同0b00000000000000000000000010010101


推荐阅读