1. 程式人生 > >codechef EBAIT Election Bait【歐幾里得演算法】

codechef EBAIT Election Bait【歐幾里得演算法】

題目分析:

歐幾里得演算法來處理一類分數問題,分數問題的形式如下

$\frac{a}{b} < \frac{p}{q} < \frac{c}{d}$

當a=0時,答案等於$\frac{1}{\lfloor \frac{d}{c} \rfloor + 1}$
當a>=b時,可以考慮前後同減去一個數化為真分數,再加上

當c>d時,因為不滿足一二,所以可以直接令答案等於$\frac{1}{1}$

否則分子分母取倒,再倒回來

程式碼:

 1 #include<bits/stdc++.h>
 2 using namespace std;
 3 
 4 const
int maxn = 1020000; 5 6 int n,C1,C2; 7 int a[maxn]; 8 9 pair<int,int> p1,p2; 10 11 void comp(pair<int,int> alpha,pair<int,int> beta){ 12 if(1ll*alpha.first*beta.second >= 1ll*alpha.second*beta.first) 13 p1 = beta; 14 } 15 16 pair<int,int> euchild(pair<int,int
> alpha,pair<int,int> beta){ 17 if(alpha.first == 0) return make_pair(1,beta.second/beta.first+1); 18 if(alpha.first >= alpha.second){ 19 int lw = alpha.first/alpha.second,hh = beta.second; 20 pair<int,int> jh = euchild(make_pair(alpha.first%alpha.second,alpha.second),make_pair(beta.first-lw*hh,hh));
21 jh.first += jh.second*lw; 22 return jh; 23 } 24 if(beta.first > beta.second) return make_pair(1,1); 25 swap(beta.first,beta.second);swap(alpha.first,alpha.second); 26 pair<int,int> jh = euchild(beta,alpha); 27 swap(jh.first,jh.second); 28 return jh; 29 } 30 31 void work(){ 32 if(n&1){puts("-1");return;} 33 p1 = make_pair(1,0); 34 int a1 = 0,a2 = 0; 35 for(int i=1;i<n;i++){ 36 if(i&1) a1 += a[i]; 37 else a2 += a[i]; 38 comp(p1,make_pair(a1,a2)); 39 } 40 a2 += a[n]; p2 = make_pair(a2,a1); swap(p1.first,p1.second); 41 if(1ll*p1.first*p2.second > 1ll*p2.first*p1.second){puts("-1");return;} 42 pair<int,int> ans = euchild(p1,p2); 43 if(ans.first <= C1 && ans.second <= C2){ 44 printf("%d %d\n",ans.first,ans.second); 45 }else puts("-1"); 46 } 47 48 int main(){ 49 int Tmp; scanf("%d",&Tmp); 50 while(Tmp--){ 51 scanf("%d%d%d",&n,&C1,&C2); 52 for(int i=1;i<=n;i++) scanf("%d",&a[i]); 53 work(); 54 } 55 return 0; 56 }