BZOJ 2242: [SDOI2011]计算器

来源:互联网 发布:谷歌搜索引擎优化指南 编辑:程序博客网 时间:2024/06/07 10:34

2242: [SDOI2011]计算器

Time Limit: 10 Sec  Memory Limit: 512 MB
Submit: 4058  Solved: 1579
[Submit][Status][Discuss]

Description

你被要求设计一个计算器完成以下三项任务:
1、给定y,z,p,计算Y^Z Mod P 的值;
2、给定y,z,p,计算满足xy≡ Z ( mod P )的最小非负整数;
3、给定y,z,p,计算满足Y^x ≡ Z ( mod P)的最小非负整数。

Input

 输入包含多组数据。

第一行包含两个正整数T,K分别表示数据组数和询问类型(对于一个测试点内的所有数据,询问类型相同)。
以下行每行包含三个正整数y,z,p,描述一个询问。

Output

对于每个询问,输出一行答案。对于询问类型2和3,如果不存在满足条件的,则输出“Orz, I cannot find x!”,注意逗号与“I”之间有一个空格。

Sample Input

【样例输入1】
3 1
2 1 3
2 2 3
2 3 3
【样例输入2】
3 2
2 1 3
2 2 3
2 3 3
【数据规模和约定】
对于100%的数据,1<=y,z,p<=10^9,为质数,1<=T<=10。

Sample Output

【样例输出1】
2
1
2
【样例输出2】
2
1
0

HINT

Source

第一轮day1

[Submit][Status][Discuss]

题解:傻逼数学题,三个任务都是模版,第一个任务快速幂没什么说的,第二个点扩展欧几里德,也没什么说的,第三个点BSGS,没什么说的。BSGS回头会写博客说明,大概在明天吧。
贴上代码:
#include<iostream>#include<stdio.h>#include<cmath>#include<string.h>#include<map>using namespace std;int T,k;int flag=0;long long  aa,bb,p;map<int,int> mp;long long cheng(long long a,long long b,long long p){    long long ans=1;    while(b>0)    {        if(b&1) ans=ans*a%p;        a=a*a%p;        b>>=1;    }    return ans;}void solve1(){    while(T--)    {        scanf("%lld%lld%lld",&aa,&bb,&p);        long long ans=cheng(aa,bb,p);        printf("%lld\n",ans);    }    return;}void ex_gcd(long long a,long long b,long long &d,long long &x,long long &y){    if(b==0)    {        x=1,y=0;        d=a;                return ;    }    ex_gcd(b,a%b,d,x,y);    long long  x0=x;    x=y;    y=x0-(a/b)*y;}void solve2(){    while(T--)    {        long long x,y,d;        scanf("%lld%lld%lld",&aa,&bb,&p);        ex_gcd(aa,p,d,x,y);        if(bb%d!=0)        {            printf("Orz, I cannot find x!\n");            continue;        }            x=x*(bb/d)%p;                x=(x%(p/d)+p/d)%(p/d);        printf("%lld\n",x);    }}void solve3(){    while(T--)    {        flag=0;        long long x,y,d;        scanf("%lld%lld%lld",&aa,&bb,&p);        aa%=p;        if(!aa&&!bb)            {            printf("1\n");            continue;        }        if(!aa)        {            printf("Orz, I cannot find x!\n");            continue;        }        mp.clear();        long long m = ceil(sqrt(p)),t = 1;        mp[1]=m+1;        for(long long i=1;i<m;i++)         {            t=t*aa%p;            if(!mp[t]) mp[t]=i;        }        long long tmp=cheng(aa,p-m-1,p),ine=1;        for(long long k=0;k<m;k++)        {            int i=mp[bb*ine%p];            if(i)            {                   flag=1;                     if(i==m+1) i=0;                printf("%lld\n",k*m+i);                break;            }            ine=ine*tmp%p;        }        if(!flag)        printf("Orz, I cannot find x!\n");    }       }int main(){    scanf("%d%d",&T,&k);    if(k==1) solve1();    if(k==2) solve2();    if(k==3) solve3();    return 0;}


原创粉丝点击