POJ1006

求满足同余方程组 x % 23 = p, x % 28 = e, x % 33 = i 的最小的x的值,答案最大不会超过21252(23*28*33)

直接枚举答案就好了,数据太水,正解应该是中国剩余定理

枚举:

#include<cstdio>
using namespace std;
int main(){
	for (int phy,emo,itl,day,cnt=0; ; ){
		scanf("%d%d%d%d", &phy, &emo, &itl, &day); ++cnt;
		if (phy==-1) break;
		phy%=23; emo%=28; itl%=33;
		for (int i=1; i<=21252; ++i){
			if (((i+day)%23==phy) && ((i+day)%28==emo) && ((i+day)%33==itl)){
				printf("Case %d: the next triple peak occurs in %d days.\n", cnt, i);
				break;
			}
		}
	}
}

 -------------------------------------------------------------------明天补充中国剩余定理------------------------------------------------

中国剩余定理:设m1,m2...mk是k个两两互素的正整数,m = m1*m2*...*mk,Mi = m / mi,1 <= i <= k

                         那么同余方程组 x≡bi ( mod mi ) 有惟一解 x ≡ b1*M1*M1'+b2*M2*M2'+...+bk*Mk*Mk'

                         其中Mi‘是Mi对于mi的逆元,即Mi*Mi'≡1 ( mod mi )

证明:对任意1 <= i , j <= k,i ≠ j 时,(mi,mj) =1,所以(Mi,mi)=1,那么存在Mi的逆元Mi',此时mj|Mi,所以对每个j满足

           b1*M1*M1'+b2*M2*M2'+...+bk*Mk*Mk' ≡ bjMjMj' ≡ bj  ( mod mj )

           则 x ≡ b1*M1*M1'+b2*M2*M2'+...+bk*Mk*Mk'为同余方程组的解

           解的惟一性在此不做证明了

 

#include<cstdio>
using namespace std;
int phy,emo,itl,day;
void ExGcd(int a,int b,int &x,int &y){
	if (!b){
		x=1; y=0;
		return;
	}
	ExGcd(b,a%b,x,y);
	int tmp=x; x=y; y=tmp-a/b*y;
}
int CRT(){
	int M[4]={0,28*33,23*33,23*28};
	int x,y,ans=0;
	ExGcd(M[1],23,x,y);
	ans=(ans+M[1]*x*phy)%21252;
	ExGcd(M[2],28,x,y);
	ans=(ans+M[2]*x*emo)%21252;
	ExGcd(M[3],33,x,y);
	ans=(ans+M[3]*x*itl)%21252;
	if (ans<0) ans+=21252;
	return ans;
}
int main(){
	for (int cnt=0; ; ){
		scanf("%d%d%d%d", &phy, &emo, &itl, &day); ++cnt;
		if (phy==-1) break;
		int ans=CRT()%21252;
		if (ans<=day) ans+=21252;
		printf("Case %d: the next triple peak occurs in %d days.\n", cnt, ans-day);
	}
	return 0;
}

 

posted @ 2016-07-26 22:33  J_Harden  阅读(108)  评论(0)    收藏  举报