算法学习:快速幂,欧拉函数,BSGS,中国剩余,卢卡斯定理板子合集

【最大公约数】

 1 ll qpow(ll a, ll x)
 2 {
 3     ll ret = 1;
 4     while (x)
 5     {
 6         if (x & 1)
 7         {
 8             ret = (ret * a) % mod;
 9         }
10         a = (a * a) % mod;
11         x >>= 1;
12     }
13     return ret;
14 }

【扩展欧几里得】

 1 void exgcd(ll a, ll b)
 2 {
 3     if (!b)
 4     {
 5         x = 1, y = 0;
 6         return;
 7     }
 8     exgcd(b, a % b);
 9     ll tmp = x;
10     x = y;
11     y = tmp - (a / b) * y;
12 }

 

【快速幂】

 1 ll qpow(ll a, ll x)
 2 {
 3     ll ret = 1;
 4     while (x)
 5     {
 6         if (x & 1)
 7         {
 8             ret = (ret * a) % mod;
 9         }
10         a = (a * a) % mod;
11         x >>= 1;
12     }
13     return ret;
14 }

【中国剩余】

 1 ll excrt(ll n)
 2 {
 3     ll x, y, k;
 4     ll M = bi[1], ans = ai[1];
 5     for (int i = 2; i <= n; i++)
 6     {
 7         ll a = M, b = bi[i], c = (ai[i] % b - ans % b + b) % b;
 8         ll gcd = exgcd(a, b, x, y);
 9         ll bg = b / gcd;
10         if (c % gcd != 0)
11             return -1;
12         x = qpow(x, c / gcd, bg);
13         ans += x * M;
14         M *= bg;
15         ans = (ans % M + M) % M;
16     }
17     return (ans % M + M + M) % M;
18 }

【BSGS】

 1 ll BSGS(ll b, ll n)
 2 {
 3     if (b % mod == 0) {
 4         
 5         return -1;
 6     }
 7     int m = (int)(sqrt(mod));
 8     mapp[n % mod] = 0;
 9     for (int i = 1; i <= m;i++) 
10     {
11         mapp[qpow(b, i) * n % mod] = i;
12     }
13     long long t = qpow(b, m), ans = 1;
14     for(int i=1;i<=m;i++)
15     {
16         ans = (ans * t) % mod;
17         if (mapp[ans])
18         {
19             long long q = i * m - mapp[ans];
20             return  ((q % mod + mod) % mod);
21         }
22     }
23     return -1;
24 }

 

posted @ 2020-05-13 23:43  rentu  阅读(202)  评论(0编辑  收藏  举报