Time Limit: 10000 ms Case Time Limit: 1000 ms Memory Limit: 256 MB
Total Submission: 59 Submission Accepted: 15
Total Submission: 59 Submission Accepted: 15
Judge By Case
Description
上完物理实验课,紧接着就上数学课,课上大名鼎鼎的Z老师按照惯例先给大家讲一个故事,今天的第一堂课当然是讲他的得意弟子青年数学家恽之玮勇夺国际数学奥林匹克(International Mathematical Olympiad,简称IMO)金牌的故事,故事讲完后,Z老师组织大家讨论了一道当年恽之玮学长遇到的难题,问题并不复杂:给你一个最简真分数,找出另一个分子分母都在1到32767之间的最简真分数,使它与给定的分数最为接近,这里最为接近指的是两数之间的差最小,如5/6就比3/4更接近4/5,因为5/6与4/5相差不到0.4,而3/4与4/5相差了0.5。所谓最简真分数也就是说分子和分母的最大公约数为1,并且分子小于分母。
Input
输入数据仅有一行包含两个用空格隔开的正整数N和D,其中1≤N<D≤32767,分别是给你的分数的分子和分母。
Output
输出数据仅有一行包含两个正整数,分别是你求出的最接近的真分数的分子和分母,并且分子分母都在1到32767之间。如果满足条件的真分数不止一个,输出其中数值最小的那个。输出时两数之间严格用一个空格隔开,行末没有多余的空格。
Sample Input
Original | Transformed |
2 3
2[SP]3[EOF]
Sample Output
Original | Transformed |
21845 32767
21845[SP]32767[EOF]
Hint
样例解释:21845/32767=0.666676839503... ≈0.666666... = 2/3。
100%的数据满足:1≤N<D≤32767
100%的数据满足:1≤N<D≤32767
Source
枚举训练
这一题,怎么说呢,虽然是直接枚举分母,但是对精度的运算不熟,考虑情况不全,导致无限debug
#include<cstdio>
#include<cmath>
#include<cstring>
#include<string>
#include<iostream>
#include<algorithm>
#include<queue>
#include<stack>
#include<sstream>
#include<map>
//#define DEBUG
const int maxn = 505;
using namespace std;
long long gcd(long long a, long long b);
int main() {
#ifdef DEBUG
freopen("Text.txt", "r", stdin);
#endif // DEBUG
cin.tie(0);
cin.sync_with_stdio(false);
long long a, b;
while (cin >> a >> b) {
int i, j, k;
double mm = 1000000.0,r;
long long x, y, ans1, ans2;
for (i = 1; i <= 32767; i++) {
if (i == b)continue;
x = 1LL * i*a / b;
y = 0;
if (i*a%b != 0)y = x + 1;
if (fabs((double)x / i - (double)a / b) > fabs((double)y / i - (double)a / b))x = y;
long long dd = gcd(x, i);
x = 1LL * x / dd;
y = 1LL * i / dd;
if (x==a&&y==b)continue;
r = fabs((double)x / y - (double)a / b);
if (r < mm) {
mm = r;
ans1 = x;
ans2 = y;
}
}
cout << ans1 << " " << ans2 << endl;
}
return 0;
}
long long gcd(long long a, long long b) {
if (b == 0)
return a;
else
return gcd(b, a%b);
}