您的位置:首页 > 其它

[UOJ 12]猜数

2017-07-31 20:21 323 查看

Description



Input



Output



Sample Input1

1
1 4

Sample Output1

4 5

Sample Explanation1


Sample Input2

1
2 8

Sample Output2

8 10

HINT



题解

此题巨坑无比。不要用$unsigned/cin$。

其次$a,b$是$g$的倍数的意思是“对于输入的$g$,$a,b$一定要是$g$的倍数”,而不是“对于所有$a,b$,输入的$g$满足$a,b$是$g$的倍数”(这种理解其实直接就是$g=1$,而输入并不保证$g=1$)。

我们有$n=l×g$。那么我们分开来讨论:

对于最小值,由均值不等式:$a+b≥2\sqrt{ab}=2\sqrt{n}=2\sqrt{lg}$(当且仅当$a=b$取等)。由于$a,b≥g$,显然可以取等,满足。

对于最大值,由于$a+b≥2\sqrt{lg}$,我们记$f(x)=a+b={n\over b}+b$,显然在$(0,\sqrt n]$是单调递减的。由于$b≥g$,故在$b=g$处取最大值。

综上最小值为$2\sqrt{lg}$,最大值为$l+g$。

精度问题
有人可能会写:

ans_min = (long long)sqrt((double)g × l);


这样会被卡精度,因为$double$大概只有$15$位$10$进制有效数字。只能得到$60$分。
解决方法是:

ans_min = (long long)sqrt(l / g) × g;


当然有人可能直接$long double$保平安了……

#include<set>
#include<map>
#include<ctime>
#include<cmath>
#include<queue>
#include<stack>
#include<cstdio>
#include<string>
#include<vector>
#include<cstring>
#include<cstdlib>
#include<iostream>
#include<algorithm>
#define LL long long
#define RE register
#define IL inline
using namespace std;

LL a,b;
int t;

int main()
{
cin>>t;
while (t--)
{scanf("%lld%lld",&a,&b);
printf("%lld %lld\n",2*(LL)sqrt(b/a)*a,a+b);}
return 0;
}
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: