zoukankan      html  css  js  c++  java
  • [SDOI2011]计算器

    洛咕

    题意:给定y,z,p,有三种操作:

    1、计算y^z mod p的值;

    2、计算满足x*y≡z(mod p)的最小非负整数x;

    3、计算满足y^x≡z(mod p)的最小非负整数x;

    分析:模板题.快速幂+扩欧+BSGS.

    #include<bits/stdc++.h>
    #define LL long long
    using namespace std;
    inline int read(){
        int s=0,w=1;char ch=getchar();
        while(ch<'0'||ch>'9'){
            if(ch=='-')w=-1;
            ch=getchar();
        }
        while(ch>='0'&&ch<='9'){
            s=s*10+ch-'0';
            ch=getchar();
        }
        return s*w;
    }
    LL ksm(LL a,LL b,LL p){
        LL cnt=1;
        while(b){
            if(b&1)cnt=(LL)(cnt*a)%p;
            a=(LL)(a*a)%p;
            b>>=1;
        }
        return cnt;
    }
    LL exgcd(LL a,LL b,LL &x,LL &y){
        if(b==0){x=1;y=0; return a;}
        LL d=exgcd(b,a%b,y,x);
        y-=(a/b)*x;
        return d;
    }
    LL BSGS(LL a,LL b,LL p){
        map<LL,LL>hash;hash.clear();
        b%=p;int t=(int)sqrt(p)+1;
        for(int j=0;j<t;j++){
            int val=(LL)b*ksm(a,j,p)%p;
            hash[val]=j;
        }
        a=ksm(a,t,p);
        if(a==0)return b==0?1:-1;
        for(int i=0;i<=t;i++){
            int val=ksm(a,i,p);
            int j=hash.find(val)==hash.end()?-1:hash[val];
            if(j>=0&&i*t-j>=0)return i*t-j;
        }
        return -1;
    }
    int main(){
        LL T=read(),k=read();
        while(T--){
        	LL y=read(),z=read(),p=read();
            if(k==1)printf("%lld
    ",ksm(y,z,p));
    //操作1,直接快速幂输出答案
            else if(k==2){
                LL x=0,yy=0,gcd=exgcd(y,p,x,yy);    
                if(z%gcd==0){//如果有解
                    LL tmp=p/gcd;
                    x=(((x*z)/gcd)%tmp+tmp)%tmp; //找到最小解
                    printf("%lld
    ",x);
                }
                else printf("Orz, I cannot find x!
    "); 
            }
            else if(k==3){
                LL ans=BSGS(y,z,p);
                if(ans==-1)printf("Orz, I cannot find x!
    ");
                else printf("%lld
    ",ans);
            }
        }
        return 0;
    }
    

    超级快的链式前向星哈希,但在正确率上有点BUG,不过洛咕还是能过的.

    #include<bits/stdc++.h>
    #define LL long long
    #define LB long double
    using namespace std;
    inline LL read(){
        LL s=0,w=1;char ch=getchar();
        while(ch<'0'||ch>'9'){if(ch=='-')w=-1;ch=getchar();}
        while(ch>='0'&&ch<='9'){s=s*10+ch-'0';ch=getchar();}
        return s*w;
    }
    int top,tou[376637];
    struct ppx{
        int p,x;LL y;
    }b[376637],c;
    inline LL ksm(LL a,LL b,LL c){
        LL cnt=1;
        while(b){
    	if(b&1)cnt=(LL)(cnt*a)%c;
    	a=(LL)(a*a)%c;
    	b>>=1;
        }
        return cnt;
    }
    inline LL exgcd(LL a,LL b,LL &x,LL &y){
        if(b==0){x=1;y=0;return a;}
        LL d=exgcd(b,a%b,y,x);
        y-=(a/b)*x;
        return d;
    }
    inline LL ksc(LL x,LL y,LL p){
        return (x*y-(LL)((LB)x/p*y)*p+p)%p;
    }
    inline void ha1(int x,LL y){
        b[++top].x=x;b[top].y=y;y%=376637;
        b[top].p=tou[y]; tou[y]=top;
    }
    inline LL BSGS(int x,LL y,LL p){
        for(int i=0;i<372637;++i)b[i]=c,tou[i]=0,top=0;
        int z=pow(p,0.5)+1;
        LL sx=1,sy=1;
        for(int i=0;i<z;++i,sx=ksc(sx,x,p))
            ha1(i,ksc(sx,y,p));
        sy=sx;
        for(int i=1;i<=z;++i,sy=ksc(sy,sx,p)){
            for(int j=tou[sy%376637];j;j=b[j].p)
                if(sy==b[j].y)return (LL)i*z-b[j].x;
        }return -1;
    }
    int main(){
        int T=read(),K=read();
        while(T--){
    	int y=read(),z=read(),p=read();
    	if(K==1)printf("%lld
    ",ksm(y,z,p));
    	else if(K==2){
    	    LL x,y0,d=exgcd(y,p,x,y0);
    	    if(z%d)printf("Orz, I cannot find x!
    ");
    	    else printf("%lld
    ",((x*z/d)%(p/d)+(p/d))%(p/d));
    	}
    	else if(K==3){
    	    if(y%p==0&&z!=0){
                    puts("Orz, I cannot find x!");
                    continue;
                }
                int ans=BSGS(y,z,p);
                if(ans!=-1)printf("%d
    ",ans);
                else puts("Orz, I cannot find x!");
    	}
        }
        return 0;
    }
    
  • 相关阅读:
    Idea中SpringBoot热部署搭建
    Redis 集群搭建
    centos7 vsftp搭建
    Centos 7 安装jdk
    Centos7 安装nginx
    Xshell 连接Linux
    python 的mysql 操作
    NIO/BIO
    java基础-3
    java基础-2
  • 原文地址:https://www.cnblogs.com/PPXppx/p/10584835.html
Copyright © 2011-2022 走看看