zoukankan      html  css  js  c++  java
  • 扩展BSGS求解离散对数问题

    扩展BSGS用于求解axΞb mod(n) 同余方程中gcd(a,n)≠1的情况

    基本思路,将原方程转化为a与n互质的情况后再套用普通的BSGS求解即可

    const int maxint=((1<<30)-1)*2+1;
    struct Hashmap{
        static const int Ha=999917,maxe=46340;
        int E,lnk[Ha],son[maxe+5],nxt[maxe+5],w[maxe+5];
        int top,stk[maxe+5];
        void clear() {E=0;while(top) lnk[stk[top--]]=0;}
        void Add(int x,int y){son[++E]=y;nxt[E]=lnk[x];w[E]=maxint;lnk[x]=E;}
        bool count(int y)
        {
            int x=y%Ha;
            for(int j=lnk[x];j;j=nxt[j])
                if(y==son[j]) return true;
            return false;
        }
        int& operator [] (int y)
        {
            int x=y%Ha;
            for(int j=lnk[x];j;j=nxt[j])
                if(y==son[j]) return w[j];
            Add(x,y);stk[++top]=x;return w[E];
        }
    };
    Hashmap f;
    int gcd(int a,int b){
        if(!b) return a;
        else return gcd(b,a%b);
    }
    int exgcd(int a,int b,int &x,int &y)
    {
        if(!b) {x=1;y=0;return a;}
        int r=exgcd(b,a%b,x,y),t=x;
        x=y;y=t-(a/b)*y;
        return r;
    }

    int exBSGS(int A,int B,int C)
    {
        if(C==1) if(!B) return A!=1;else return -1;
        if(B==1) if(A) return 0;else return -1;
        if(A%C==0) if(!B) return 1;else return -1;
        int r,D=1,num=0;
        while((r=gcd(A,C))>1)
        {
            if(B%r) return -1;num++;
            B/=r;C/=r;D=((ll)D*A/r)%C;
        }
        for(int i=0,now=1;i<num;i++,now=((ll)now*A)%C)
        {
            if(now==B) return i;
        }
        int m=ceil(sqrt(C)),Base=1;f.clear();
        for(int i=0;i<=m-1;i++)
        {
            f[Base]=min(f[Base],i);
            Base=((ll)Base*A)%C;
        }
        for(int i=0;i<=m-1;i++)
        {
            int x,y,r=exgcd(D,C,x,y);
            x=((ll)x*B%C+C)%C;
            if(f.count(x)) return i*m+f[x]+num;
            D=((ll)D*Base)%C;
        }
        return -1;
    }
  • 相关阅读:
    关于在组件GIS开发中使用Python的一点补充说明
    shell环境变量以及set,env,export的区别
    快速配置 Samba 将 Linux 目录映射为 Windows 驱动器
    Expect 教程中文版
    rpm 包管理
    .bash_profile和.bashrc的什么区别
    grep 零宽断言
    自动化测试
    dialog shell下的gui设计 代替繁杂libncurses编程
    x11 gtk qt gnome kde 之间的区别和联系
  • 原文地址:https://www.cnblogs.com/033000-/p/10087321.html
Copyright © 2011-2022 走看看