zoukankan      html  css  js  c++  java
  • Poj 2417 babystep 素数

    解方程 a^x=b(mod c) c为素数,用算法babystep,水过的,4s多

    #include <iostream>

    #include <stdio.h>

    #include <cmath>

    using namespace std;

    typedef long long ll;

    const ll maxn=65535;

    struct Hashh

    {

    ll a,b,next;

    }Hash[maxn<<1];

    ll flag[maxn+100];//注意要赋初值0

    ll top,idx;//注意要赋初值maxn

    void ins(ll a,ll b)

    {

    ll k=b&maxn;//maxn=11…111,若比maxn大,取前16位,否则与原freopen("in.txt","r",stdin);相等

    if(flag[k]!=idx)//第b&maxn个槽为空

    {

    flag[k]=idx;

    Hash[k].a=a;

    Hash[k].b=b;

    Hash[k].next=-1;

    return ;

    }

    //第b&maxn个槽不为空

    while(Hash[k].next!=-1)//到链表的最后一个

    {

    if(Hash[k].b==b) return;//若b已经存在,返回

    k=Hash[k].next;

    }

    Hash[k].next=++top;

    Hash[top].next=-1;

    Hash[top].a=a;

    Hash[top].b=b;

    }

    ll find(ll b)

    {

    ll k=b&maxn;

    if(flag[k]!=idx) return -1;//为空

    while(k!=-1)

    {

    if(Hash[k].b==b) return Hash[k].a;

    k=Hash[k].next;

    }

    return -1;

    }

    ll gcd(ll a,ll b){if(b==0)return a;return gcd(b,a%b);}

    ll mulmod(ll a,ll b,ll n)

    {

    ll ret=0;

    a%=n;

    while(b>=1)

    {

    if(b&1)

    {

    ret+=a;

    if(ret>=n) ret-=n;

    }

    a<<=1;

    if(a>=n) a-=n;

    b>>=1;

    }

    return ret;

    }

    ll exmod(ll a,ll b,ll n)

    {

    ll ret=1;

    a%=n;

    while(b>=1)

    {

    if(b&1)

    ret=mulmod(ret,a,n);

    a=mulmod(a,a,n);

    b>>=1;

    }

    return ret;

    }

    ll exgcd(ll a,ll b,ll &x,ll &y)

    {

    if(0==b) {x=1;y=0;return a;}

    ll d=exgcd(b,a%b,x,y);

    ll t=x;x=y;y=t-a/b*y;

    return d;

    }

    ll invmod(ll a,ll n)

    {

    ll x,y;

    if(exgcd(a,n,x,y)!=1)return -1;

    return (x%n+n)%n;

    }

    ll babystep(ll a,ll b,ll c)

    {

    top=maxn;idx++;

    ll tmp,r=b,w;

    ll m=(ll)ceil(sqrt((double)(c-1)));

    ins(0,1);

    for(ll i=1;i<=m;i++) {ins(i,exmod(a,i,c));}

    tmp=invmod(exmod(a,m,c),c);

    for(ll i=0;i<=m-1;i++)

    {

    w=find(r);

    if(w!=-1){return i*m+w;}

    r=(r*tmp%c+c)%c;

    }

    return -1;

    }

    int main()

    {

    ll a,b,c,tmp;

    freopen("in.txt","r",stdin);

    while(scanf("%lld%lld%lld",&c,&a,&b)!=EOF)

    {

    b%=c;

    tmp=babystep(a,b,c);

    if(tmp<0) printf("no solution\n");

    else printf("%lld\n",tmp);

    }

    return 0;

    }

    改进了一下,刷到32ms

     1 #include <iostream>
    2 #include <stdio.h>
    3 #include <cmath>
    4 using namespace std;
    5 typedef long long ll;
    6 const int maxn=65535;
    7 struct Hashh
    8 {
    9 int a,b,next;
    10 }Hash[maxn<<1];
    11 int flag[maxn+100];//注意要赋初值0
    12 int top,idx;//注意要赋初值maxn
    13 void ins(int a,int b)
    14 {
    15 int k=b&maxn;//maxn=11…111,若比maxn大,取前16位,否则与原freopen("in.txt","r",stdin);相等
    16 if(flag[k]!=idx)//第b&maxn个槽为空
    17 {
    18 flag[k]=idx;
    19 Hash[k].a=a;
    20 Hash[k].b=b;
    21 Hash[k].next=-1;
    22 return ;
    23 }
    24 //第b&maxn个槽不为空
    25 while(Hash[k].next!=-1)//到链表的最后一个
    26 {
    27 if(Hash[k].b==b) return;//若b已经存在,返回
    28 k=Hash[k].next;
    29 }
    30 Hash[k].next=++top;
    31 Hash[top].next=-1;
    32 Hash[top].a=a;
    33 Hash[top].b=b;
    34 }
    35
    36 int find(int b)
    37 {
    38 int k=b&maxn;
    39 if(flag[k]!=idx) return -1;//为空
    40 while(k!=-1)
    41 {
    42 if(Hash[k].b==b) return Hash[k].a;
    43 k=Hash[k].next;
    44 }
    45 return -1;
    46 }
    47
    48 int gcd(int a,int b){if(b==0)return a;return gcd(b,a%b);}
    49 int exgcd(int a,int b,int &x,int &y)
    50 {
    51 if(0==b) {x=1;y=0;return a;}
    52 int d=exgcd(b,a%b,x,y);
    53 int t=x;x=y;y=t-a/b*y;
    54 return d;
    55 }
    56
    57 int exmod(ll a,int b,int c)
    58 {ll ret=1%c;a%=c;while(b){if(b&1)ret=ret*a%c;a=a*a%c;b>>=1;}return ret;}
    59
    60 int invmod(int a,int n)
    61 {
    62 int x,y;
    63 if(exgcd(a,n,x,y)!=1)return -1;
    64 return (x%n+n)%n;
    65 }
    66
    67 int babystep(int a,int b,int c)
    68 {
    69 top=maxn;idx++;
    70 ll buf=1%c,r=b,tmp;
    71 int w,i;
    72 int m=(int)ceil(sqrt((double)(c-1)));
    73 for(i=0;i<=m;i++) {ins(i,buf);buf=buf*a%c;}
    74 tmp=invmod(exmod(a,m,c),c);
    75 for(i=0;i<=m-1;i++)
    76 {
    77 w=find(r);
    78 if(w!=-1){return i*m+w;}
    79 r=(r*tmp%c+c)%c;
    80 }
    81
    82 return -1;
    83 }
    84
    85
    86 int main()
    87 {
    88 int a,b,c,tmp;
    89 freopen("in.txt","r",stdin);
    90 while(scanf("%d%d%d",&c,&a,&b)!=EOF)
    91 {
    92 b%=c;
    93 tmp=babystep(a,b,c);
    94 if(tmp<0) printf("no solution\n");
    95 else printf("%d\n",tmp);
    96 }
    97 return 0;
    98 }



  • 相关阅读:
    flask 使用Flask-SQLAlchemy管理数据库(连接数据库服务器、定义数据库模型、创建库和表) --
    flask 操作数据库(分类) --
    flask渲染模板时报错TypeError: 'UnboundField' object is not callable --
    flask用宏渲染表单模板时,表单提交后,如果form.validate_on_submit()返回的是false的可能原因 --
    flask 单个页面多个表单(单视图处理、多视图处理) --
    flask 单个表单多个提交按钮 --
    jython 2.7.1 版本开发历史
    TP v5中Url Compat模式
    乱弹
    改改"坏"代码
  • 原文地址:https://www.cnblogs.com/inpeace7/p/2406549.html
Copyright © 2011-2022 走看看