题目描述
X星球的某个大奖赛设了M级奖励。每个级别的奖金是一个正整数。
并且,相邻的两个级别间的比例是个固定值。
也就是说:所有级别的奖金数构成了一个等比数列。比如:16,24,36,54 其等比值为:3/2
现在,我们随机调查了一些获奖者的奖金数。
请你据此推算可能的最大的等比值。
输入格式:
第一行为数字 N (0<N<100),表示接下的一行包含N个正整数
第二行N个正整数Xi(Xi<1 000 000 000 000),用空格分开。每个整数表示调查到的某人的奖金数额
要求输出:
一个形如A/B的分数,要求A、B互质。表示可能的最大比例系数
输入样例
3
1250 200 32
输出
25/4
思路
-
根据题目描述,随机调查的奖金是等比数列中的某项,那么这些奖金可能值是重复的,所以我们要对数据 先排序,后去重
-
再来研究一下等比数列
有这样一组等比数列:a1, a2, a3 ,a4 …… an-1 ,an
假设我们挑出来的奖金是:a1 ,ax , ay ,ak (注:首项就可看作a1,该序列已经排序去重)
我们要求奖金的最大比值,设为 q (等比且非递减,虽然题上没有说,但奖金怎么非递减呢)
那么根据等比数列的性质,ax = a1 × qx,ay =a1× qy ,ak = a1× qk
那么他们之间两两相邻的比值为 qx ,qy-x ,qk-x-y
-
qx ,qy-x ,qk-x-y 它们之间有一个性质:若 q 为分数,若q[ i ] > q[ j ] ,那么q[ i ] 的分子一定大于q[ j ] 的分子,q[ i ] 的分母也大于 q[ j ] 的分母;若 q 为整数,q[ i ]分子还是比q[ j ]大(因为奖金等比且非递减,虽然题上没有说,但奖金怎么递减呢 )
-
所以对于求出的 qx ,qy-x ,qk-x-y 可以根据此性质从按照分子的大小从小到大排序。
-
-
上述操作,究其原因,我也不明白(能力有限)。但答案 q ans , ans是 x,y-x,k-y-x 的最大公约数
#include<stdio.h>
#include<vector>
#include<algorithm>
#include<queue>
struct node{
long long x,y;// x为 分子 ,y 为分母
};
long long getGcd(long long a,long long b){
return b==0?a:getGcd(b,a%b);
}
bool comp(node a,node b) {
return a.x<b.x;
}
using namespace std;
int main()
{
int n;
scanf("%d",&n);;
long long arr[10010];
for(int i=0;i<n;i++){
scanf("%lld",&arr[i]);
}
//去重操作
sort(arr,arr+n);
vector<long long>v;
v.push_back(arr[0]);
for(int i=1;i<n;i++){
if(v[v.size()-1]!=arr[i])
v.push_back(arr[i]);
}
vector<node>q;
node temp;
for(int i=1;i<v.size();i++){
//求出比例
long long gcd = getGcd(v[i],v[i-1]);
temp.x=v[i]/gcd;
temp.y=v[i-1]/gcd;
q.push_back(temp);
}
sort(q.begin(),q.end(),comp);
long long minx=q[0].x;//q是分数 分子分母决定大小 q为整数 分子同样也能决定大小 ,分母为 1
long long x=q[0].x,y=q[0].y;
for(int i=1;i<q.size();i++){
if(minx>q[i].x/q[i-1].x&&q[i].x/q[i-1].x!=1){
//如果分子相同 那么分母也相同 否则不等比
x=q[i].x/q[i-1].x;
y=q[i].y/q[i-1].y;
}
}
printf("%lld/%lld",x,y);
return 0;
}