最近在写大数运算,用unsigned的基本数据类型(可能是unsigned char,也可能是unsigned int,等等)作为每一节的类型,要判断是否需要进位。
我先用了if (a + b > a) {...}else {...}
,结果判断结果总是为真,改成Data temp = a + b;if (temp > a){...}else {...}
就是对的,我觉得不太优美就又想了一下,用了if (a > ~b){...}else{...}
结果又总是判断为真,改成Data temp = ~b;if (a > temp){...}else{...}
是对的。
这下答案似乎很明显了。我又用std::cout << ~b;
看了一下,发现输出果然是负数,写成if (a > static_cast<Data>(~b)){...}else{...}
就好了。
意思就是说,~运算符可能会把unsigned的类型变成signed的一个类型。为了探究具体情况,我用其他类型试了试,发现unsigned int好像不会这样。
(我用的是VS2019 Community,DEV C++试了一下也存在类似情况,但是没有深入探究,Linux下的编译器留待各位再做试探。)
x64/x86结果都如下:
unsigned char a = 0x1;std::cout << sizeof(a);
输出4。
unsigned short a = 0x1;std::cout << sizeof(a);
输出4。
unsigned int a = 0x1;std::cout << sizeof(a);
输出4。
unsigned long a = 0x1;std::cout << sizeof(a);
输出4。
unsigned long long a = 0x1;std::cout << sizeof(a);
输出8。
结合更多的测试,我猜测按位取反时如果操作数比int短,先把操作数拓宽到int后再按位取反,如果不短于int就没这么个操作。如果有清楚历史原因的兄弟,可以在评论区告诉我,感激不尽。
……我刚才又测试了一下a + b,发现两个unsigned short相加的结果也变成了int,而且看起来也是先拓宽为int,再相加。int真是数据类型之王啊……