C++ 不要将有符号整数和无符号整数相加

有符号整数和无符号整数相加时,把负数转换成无符号数类似于直接给无符号数赋一个负值,结果等于这个负数加上无符号数的模。

unsigned int n = 300;
int m = -500;
cout << m + m << '\n';
cout << n + m << '\n';

输出:

-1000        // 正确
4294967096   // 错误

结果做个类型转换后,貌似是对的:

int nm = n + m; 

这样输出nm-200

当有符号的数值绝对值小于等于无符号的时候好像算的是对的(vs2015)。

unsigned int n = 300;
int m = -200;
cout << m + m << '\n';
cout << n + m << '\n';

输出:

-400
100
unsigned int n = 300;
int m = -300;
cout << m + m << '\n';
cout << n + m << '\n';

输出:

-600
0

当从无符号数中减去一个值时,不管这个值是不是无符号数,我们都必须确保结果不能是一个负值:

unsigned ul=42, u2=10;
std::cout<<ul-u2<< std::endl;//正确:输出 32
std::cout<<u2-ul<< std::endl;//正确:不过,结果是取模后的值 4294967264

输出:

32
4294967264

无符号数不会小于0这一事实同样关系到循环的写法。例如,在 1.4.1节的练习(第11页)中需要写一个循环,通过控制变量递减的方式把从10到0的数字降序输出。这个循环可能类似于下面的形式:

// 这个时对的
for(inti=10;i>=0;--i)
    std::cout<<i<< std::endl;

下面这种写法永远退不出循环:

//错误:变量u永远也不会小于0,循环条件一直成立
for(unsignedu=10;u>=0;--u)
   std::cout<<u<< std::endl;

所以,一定不要混用无符号整数和有符号整数,不能将负数赋值给无符号变量。

相乘,也是不对的。

unsigned a = 1;
int b = -1;
cout << a * b << '\n';

输出:

4294967295    // 不对,你可能期望的时 -1。将这个数强转成有符号,它就是 -1




参考:《C++ Primer》 P34
posted @   double64  阅读(69)  评论(0编辑  收藏  举报
相关博文:
阅读排行:
· 全程不用写代码,我用AI程序员写了一个飞机大战
· MongoDB 8.0这个新功能碉堡了,比商业数据库还牛
· DeepSeek 开源周回顾「GitHub 热点速览」
· 记一次.NET内存居高不下排查解决与启示
· 白话解读 Dapr 1.15:你的「微服务管家」又秀新绝活了
历史上的今天:
2021-09-11 三菱 PLC FX3U 系列接近开关接线+中间继电器控制电机启停接线
点击右上角即可分享
微信分享提示