从零下8度到零上8度,C++这把魔法棒叫abs
小时候学算术,老师总说“距离没有负数”。后来写代码,我发现C++里藏着一位忠实执行这个规则的函数——不管你丢给它正数还是负数,它都还你一个非负的结果。它就是 abs。
如果你还没意识到它的强大,想想这些场景:计算两个坐标之间的距离、求温度差的绝对值、判断两个数是否相差在某个范围内……这些都需要把一个可能为负的差值变成正数。而 abs 正是为此而生。
一、abs 是什么?怎么用?
先看最简单的例子。假设你记录了一天的气温变化,有个温度是零下8度:
int temperature = -8;
int absTemp = abs(temperature); // 8
abs 返回的是参数在数轴上到0点的距离,所以永远是非负的。无论你传 5 还是 -5,结果都是 5。
要使用它,记得包含头文件:整数用 #include <cstdlib>,浮点数用 #include <cmath>(或 fabs)。虽然很多编译器两个都兼容,但养成规范习惯总没错。
一个经常被问到的C++基础题:要使用abs函数计算整数的绝对值,应该包含哪个头文件? 答案就是 <cstdlib>。而另一个判断题:abs(-5) 和 abs(5) 的返回值都是 5——当然正确,因为绝对值只关心距离,不关心方向。
二、实战一:还差几天到2023年?
题目是这样:给定2022年某月某日,输出距离2023年1月1日还有多少天。比如输入12月1日,输出31(因为12月有31天)。
这题其实不需要abs,因为2022年内的任何一天到2023年1月1日的天数都是正数。但假如题目改成“计算两个任意日期之间的天数差”,差值就可能为负,这时候就需要abs来取绝对值。很多初学者写日期计算时,会先判断谁大谁小,再手动交换,其实 abs(diff) 一行搞定。
顺便提一下,这题的思路很简单:先算出给定日期是2022年的第几天,再用365(或366,但2022不是闰)减去这个天数。比如:
int daysOfMonth[] = {31,28,31,30,31,30,31,31,30,31,30,31};
int total = 0;
for(int i=0; i<month-1; i++) total += daysOfMonth[i];
total += day;
int result = 365 - total; // 或 366,但2022年不是闰年
虽然没有显式用到 abs,但你在写更通用的日期差函数时,abs 会让代码更简洁、更不容易出错。
三、实战二:矩形面积交
这道题更有意思。给定两个边平行于坐标轴的矩形,每个矩形用一对相对顶点坐标表示(注意:可能给的是左上和右下,或左下和右上,需要处理)。要求输出它们相交部分的面积。
核心是求出矩形在x轴和y轴上的投影重叠长度,然后相乘。比如矩形A在x轴上的区间是 [min(x1,x2), max(x1,x2)],矩形B同理。那么重叠长度 = max(0, min(右边界) - max(左边界) )。这里面每个边界都是绝对坐标,但当你计算差值时,实际上就是在对两个端点求差——而距离永远为正,这正好是 abs 的用武之地。
更具体地说,当你需要从两个点中取出最小和最大的坐标时,可能会写出这样的代码:
double left = max(min(x1,x2), min(x3,x4));
double right = min(max(x1,x2), max(x3,x4));
double width = max(0.0, right - left);
其实 right - left 本身就是差值,如果重叠为负,width就是0。但如果你要计算两个矩形中心之间的距离,就一定会用到 abs。比如:
double cx1 = (x1+x2)/2, cx2 = (x3+x4)/2;
double dx = abs(cx1 - cx2);
这种场景下,abs 的重要性才完全凸显。很多新手会手动写 if (a<b) a-b else b-a,既啰嗦又易错。用 abs 不仅代码更优雅,还能避免除0或符号错误。
四、一点提醒
abs对int、long、long long都适用,浮点数用fabs。- 注意头文件:整数用
<cstdlib>,浮点数用<cmath>。虽然很多集成开发环境会自动包含,但严谨的项目里缺失头文件会导致编译错误,考试中更是扣分点。 - 大整数注意溢出:
abs(INT_MIN)在32位系统上会返回INT_MIN(因为绝对值超出了int范围),需要特殊处理。
五、从绝对值到更多
abs 是C++中最基础也最容易被低估的函数之一。它小到只有一行代码,却能让你的逻辑清晰度大幅提升。试着在你的代码中找出所有手动取绝对值的 if 分支,改成 abs——你会发现阅读成本瞬间降低。
下次遇到需要距离、偏差、误差的场景,别自己写判断了,让 abs 来帮你“转负为正”。毕竟,编程不只是写对代码,更是写出让人一眼看懂的代码。
关于作者
我是赵老师,持有 NOI 信息学奥赛教练证书,拥有 15 年以上的软件开发经验,从事信息学少儿编程教学已有 8 年时间。
这些年累计帮助 多名 学生通过编程特长升入自己心仪的目标学校。
如果你在编程学习上有任何疑问,欢迎联系我:18620372957(微信同号)