题意
给出T组数据,每次每组数据给出a、b、c三个数,范围在 (left[-2^{63}, 2^{63} ight]) ,
如果a+b<=c输出false,a+b>c输出true 。
思路
话说我没啥思路其实,考虑过一位一位相加去判断,但是最后觉得代码肯定又长又乱还得调,于是乎,放弃了。
第一种思路:
-
利用 正溢出后值小于0,负溢出后值大于等于0 这个知识点
-
当a<0&&b<0&&a+b>=0,为负溢出,所以a+b<=c,输出false
当a>0&&b>0&&a+b<0,为正溢出,所以 a+b>c,输出true -
代码见AC代码一。
第二种思路:
-
直接利用long double的数据范围去进行加减判断大小即可。(double会一组数据都过不去)
-
long double是C99里面新增的数据类型,相关内容可以查看:https://blog.csdn.net/hunzhangzui9837/article/details/85222209
-
代码见AC代码二。
注意
-
比赛用scanf、printf,不要用cin cout,会出现奇怪的错误
-
尽量把需要多次用到的数据都放在一个变量中,比如 ll w=a+b
-
long double输入用 %LF 或者 %llf
-
int最大: (2^{31}-1)、long long最大:(2^{63}-1)
AC代码一
#include<iostream>
#include<stdio.h>
using namespace std;
typedef long long ll;
int main()
{
int T;
cin>>T;
int cas=1;
while(T--)
{
ll a,b,c;
// cin>>a>>b>>c;
scanf("%lld %lld %lld",&a,&b,&c);
ll w=a+b;
if(a<0&&b<0&&w>=0) printf("Case #%d: false
",cas++);
else if(a>0&&b>0&&w<0) printf("Case #%d: true
",cas++);
else if(w<=c) printf("Case #%d: false
",cas++);
else if(w>c) printf("Case #%d: true
",cas++);
}
return 0;
}
AC代码二
这份代码用cin cout输入输出也可以过
#include<iostream>
#include<stdio.h>
using namespace std;
typedef long long ll;
//a+b<=c输出false a<0&&b<0&&a+b>=0
// a+b>c输出true a>0&&b>0&&a+b<0 正溢出
int main()
{
int T;
cin>>T;
int cas=1;
while(T--)
{
long double a,b,c;
scanf("%llf %llf %llf",&a,&b,&c); // long double输入用%LF或者%llf
printf("Case #%d: %s
",cas++,a+b>c?"true":"false");
}
return 0;
}
遗留的问题
-
为什么我往PTA上面提交相同的一份代码,每次每个测试点的耗时都不一样?
这个博客可以参考看一下,但是我还是觉得存在问题:https://www.zhihu.com/question/23678530/answer/25374602 -
为什么代码一里面的输入把cin改成scanf就对了,不然PTA上第三个测试点错误。
-
在cin cout输入输出的时候,把a+b的和存起来就可以对两组数据,否则就只对一组
-
但是思路二利用long double,但是long double只是精确到18位小数,我觉得并不满足题目给定的数据范围,但是不知道为什么可以AC,可能数据测试点少!?