zoukankan      html  css  js  c++  java
  • 数论模板

    数论模板

    就保存一下模板

    P3811 【模板】乘法逆元

    //递推
    #include <cstdio>
    #include <cstring>
    #include <algorithm>
    
    long long inv[3000010];
    
    int main() {
    	int n,p;
    	scanf("%d%d",&n,&p);
    	inv[1] = 1;
    	printf("1
    ");
    	for(int i = 2; i <= n; i++)
    	{
    		inv[i] = ((1ll * (-p / i) * inv[p % i] % p) + p) % p;
    		printf("%d
    ",inv[i]);
    	}
    	return 0;
    }
    
    // 费马小定理 p为素数
    #include <cstdio>
    #include <algorithm>
    #include <cstring>
    
    using namespace std;
    
    int poww(long long a,long long b)
    {
    	long long temp = 1,p = b-2;
    	while(p)
    	{
    		if(p&1 == 1) temp = temp*a%b;
    		a = a*a % b;
    		p >>= 1;
    	}
    	return temp;
    }
    
    int main() {
    	int n,p;
    	scanf("%d%d",&n,&p);
    	for(int i = 1; i <= n; i++)
    	{
    		long long ans = 0;
    		ans = poww(i,p);
    		printf("%lld
    ",ans);
    	}
    	return 0;
    }
    

    还有个exgcd


    欧拉定理/扩展欧拉定理

    【模板】欧拉定理

    //单点求phi 模板题ac
    #include <cstdio>
    #include <cstring>
    #include <algorithm>
    #include <cctype>
    
    using namespace std;
    
    long long a, m, b, flag, ans = 1, phi, tmp;
    char t;
    
    void ksm(long long a, long long b, long long c) {
    	a %= c;
    	while(b) {
    		if(b & 1) {
    			ans = (ans * a) % c;
    		}
    		a = (a * a) % c;
    		b >>= 1;
    	}
    }
    
    int main() {
    	scanf("%lld%lld", &a, &m);
    	tmp = phi = m;
    	for(long long i = 2; i * i <= m; i++) {
    		if(tmp % i == 0) {
    			phi -= (phi / i);
    			while(tmp % i == 0) {
    				tmp /= i;
    			}
    		}
    	}
    	if(tmp > 1) 
    		phi -= (phi / tmp);
    	while(!isdigit(t = getchar()));
    	for(; isdigit(t); t = getchar()) {
    		b = b * 10 + t - '0';
    		if(b >= phi) {
    			flag = 1;
    			b %= phi;
    		}
    	}
    	if(flag) {
    		b += phi;
    	}
    	ksm(a, b, m);
    	printf("%lld", ans);
    	return 0;
    } 
    
    //递推求phi 模板题24分
    #include <cstdio>
    #include <cstring>
    #include <algorithm>
    #include <vector>
    #include <queue>
    #include <string>
    typedef int int_;
    #define int long long
    
    bool vis[1000007];
    int pri[1000007], phi[1000007], cnt, temp, ans, lenm, lent, bns, m, a;
    char strr[20000007];
    
    inline void getphi(int n) {
    	vis[0] = vis[1] = 1;
    	phi[1] = 1;
    	for(int i = 2; i <= n; i++)
    	{
    		if(vis[i] == 0)
    		{
    			pri[++cnt] = i;
    			phi[i] = i - 1;
    		}
    		for(int j = 1; j <= cnt && pri[j] * i <= n; j++)
    		{
    			int next = pri[j] * i;
    			vis[next] = 1;
    			if(i % pri[j] == 0)
    			{
    				phi[next] = phi[i] * pri[j];
    				break;
    			}
    			phi[next] = phi[i] * (pri[j] - 1);
    		}
    	}
    }
    
    inline int ksm(int a, int b, int mod)
    {
    	int ret = 1;
    	while(b > 0)
    	{
    		if(b & 1) ret *= a, ret %= mod;
    		a *= a;
    		a %= mod;
    		b >>= 1;
    	}
    	return ret;
    }
    
    int_ main() {
    	scanf("%lld%lld", &a, &m);
    	getphi(m);
    	lenm = phi[m];
    	while(lenm > 0)
    	{
    		lenm /= 10;
    		lent++;
    	}
    	scanf("%s", strr);
    	int len = strlen(strr), t = 1;
    	for(int i = len - 1; i >= 0; i--)
    	{
    		temp = strr[i] - '0';
    		ans += (t * temp);
    		ans %= phi[m];
    		t *= 10;
    		t %= phi[m];
    	}
    	ans %= phi[m];
    	bns = ksm(a, ans, m);
    	if(ans == 0) bns = 0; 
    	printf("%lld", bns);
    	return 0;
    }
    

    P3390 【模板】矩阵快速幂

    #include <cstdio>
    #include <algorithm>
    #include <cstring>
    typedef int int_;           
    #define int long long       
    const int mod = 1e9 + 7;
    
    struct MAT{
        int A[110][110];
        int x, y;
        MAT(int x_, int y_)
        {
            x = x_, y = y_;
            for(int i = 1; i <= x; i++)
                for(int j = 1; j <= y; j++)
                    A[i][j] = 0;
        }
        void init(bool flg)
        {
            for(int i = 1; i <= x; i++)
                for(int j = 1; j <= y; j++)
                    A[i][j] = 0;
            if(flg) 
                for(int i = 1; i <= x; i++) A[i][i] = 1;
        }
        MAT operator*(MAT b)
        {
            MAT a = *this;
            MAT c(a.x, b.y);
            c.init(0);
            for(int i = 1; i <= a.x; i++)
                for(int j = 1; j <= b.y; j++)
                    for(int l = 1; l <= a.y; l++)
                    {
                        c.A[i][j] += a.A[i][l] * b.A[l][j];
                        c.A[i][j] %= mod;
                    }
            return c;
        }
        MAT operator^(int b)
        {
            MAT ret(x, x), a = *this;
            ret.init(1);
            while(b)
            {
                if(b&1) ret = ret * a;
                b >>= 1;
                a = a * a;
            }
            return ret;
        }
        void output()
        {
            for(int i = 1; i <= x; i++)
            {
                for(int j = 1; j <= y; j++)
                    printf("%lld ", A[i][j]);
                puts("");
            }
        }
    };
    
    int_ main() {
        int n, m, k;
        scanf("%lld%lld", &n, &k);
        MAT a(n, n);
    	
        for(int i = 1; i <= n; i++)
            for(int j = 1; j <= n; j++)
                scanf("%lld", &a.A[i][j]);
        MAT c = a ^ k;
        c.output();
    }
    

    P3807 【模板】卢卡斯定理

    #include <cstdio>
    #include <cstring>
    #include <algorithm>
    
    using namespace std;
    //I AK IOI
    long long T, n, m, p;
    long long jc[100007];
    
    long long ksm(long long a, long long b, long long c) {
    	a %= c;
    	long long ret = 1;
    	while(b != 0) {
    		if(b & 1) ret = ret * a % c;
    		b >>= 1;
    		a = a * a % c;
    	}
    	return ret % c;
    }
    
    long long cm(long long a, long long b, long long c) {
    	if(b > a) return 0;
    	return (jc[a] * ksm(jc[b], c - 2, c) % c * ksm(jc[a - b], c - 2, c) % c) % c;
    }
    
    long long lucas(long long a, long long b, long long c) {
    	if(b == 0) return 1;
    	return cm(a % c, b % c, c) * lucas(a / c, b / c, c) % c;
    } 
    
    int main() {
    	scanf("%lld", &T);
    	jc[0] = 1;
    	while(T--) {
    		scanf("%lld%lld%lld", &n, &m, &p);
    		for(long long i = 1; i <= p; i++) jc[i] = jc[i - 1] * i % p;
    		printf("%lld
    ", lucas(m + n, n, p));
    	}
    } 
    

    P1939 【模板】矩阵加速(数列)

    #include <cstdio>
    #include <algorithm>
    #include <cstring>
    typedef int int_;           
    #define int long long       
    const int mod = 1e9 + 7;
    
    struct MAT{
        int A[110][110];
        int x, y;
        MAT(int x_, int y_)
        {
            x = x_, y = y_;
            for(int i = 1; i <= x; i++)
                for(int j = 1; j <= y; j++)
                    A[i][j] = 0;
        }
        void init(bool flg)
        {
            for(int i = 1; i <= x; i++)
                for(int j = 1; j <= y; j++)
                    A[i][j] = 0;
            if(flg) 
                for(int i = 1; i <= x; i++) A[i][i] = 1;
        }
        MAT operator*(MAT b)
        {
            MAT a = *this;
            MAT c(a.x, b.y);
            c.init(0);
            for(int i = 1; i <= a.x; i++)
                for(int j = 1; j <= b.y; j++)
                    for(int l = 1; l <= a.y; l++)
                    {
                        c.A[i][j] += a.A[i][l] * b.A[l][j];
                        c.A[i][j] %= mod;
                    }
            return c;
        }
        MAT operator^(int b)
        {
            MAT ret(x, x), a = *this;
            ret.init(1);
            while(b)
            {
                if(b&1) ret = ret * a;
                b >>= 1;
                a = a * a;
            }
            return ret;
        }
    };
    
    int_ main() {
        int T;
        scanf("%lld", &T);
    	while(T--)
    	{
    		int q;
    		scanf("%lld", &q);
    		if(q <= 3)
    		{
    			printf("1
    ");
    			continue;
    		}
    		MAT ans(3, 3), chen(3, 1);
    		ans.A[1][1] = ans.A[1][3] = ans.A[2][1] = ans.A[3][2] = 1;
    		chen.A[1][1] = chen.A[2][1] = chen.A[3][1] = 1;
    		ans = ans ^ (q - 3);
    		ans = ans * chen;
        	printf("%lld
    ", ans.A[1][1]);
    	}
    	return 0;
    }
    

    P1226 【模板】快速幂||取余运算

    #include <cstdio>
    #include <cstring>
    #include <algorithm>
    
    using namespace std;
    
    int poww(long long a,long long b,long long c)
    {
    	long long temp = 1;
    	while(b)
    	{
    		if(b&1 == 1) temp = temp*a%c;
    		a = a * a % c;
    		b >>= 1;
    	}
    	return temp;
    }
    
    int main() {
    	long long b,p,k,ans;
    	scanf("%lld%lld%lld",&b,&p,&k);
    	ans = poww(b,p,k)%k;
    	printf("%d^%d mod %d=%d",b,p,k,ans);
    	return 0;
    }
    

    excrt

    #include <cstdio>
    #include <cstring>
    #include <algorithm>
    
    using namespace std;
    
    long long n, a[100007], p[100007];
    
    long long ksc(long long x, long long y, long long mod) {
    	long long ret = 0;
    	while(y > 0) {
    		if(y & 1) ret = (ret + x) % mod;
    		y >>= 1;
    		x = (x + x) % mod;
     	}
     	return (ret % mod + mod) % mod;
    }
    
    long long exgcd(long long m, long long n, long long &x, long long &y) {
    	if(n == 0) {
    		x = 1;
    		y = 0;
    		return m;
    	}
    	long long res = exgcd(n, m % n, y, x);
    	y -= (m / n) * x;
    	return res;
    }
    
    long long excrt() {
    	long long A = a[1], P = p[1], x, y;
    	for(long long i = 2; i <= n; i++) {
    		long long a1 = P, b1 = p[i], c = ((a[i] - A) % b1 + b1) % b1;
    		long long gcd = exgcd(a1, b1, x, y), bg = b1 / gcd;
    		if(c % gcd != 0) return -1;//判无解
    		x = ksc(x, c / gcd, bg);
    		A += x * P;
    		P *= bg;
    		A = (A % P + P) % P;
    	}
    	if(A == 0) A = P;
    	return A;
    }
    
    int main() {
    //	freopen("111.in", "r", stdin);
    	scanf("%lld", &n);
    	for(long long i = 1; i <= n; i++) {
    		scanf("%lld%lld", &p[i], &a[i]);
    	}
    	printf("%lld", excrt());
    	return 0;
    } 
    

  • 相关阅读:
    golang 简易聊天
    golang 自定义封包协议(转的)
    PHP 7 测试用例(转)
    android 百度地图开发
    Android studio 签名使用转
    百度ueditor 拖文件或world 里面复制粘贴图片到编辑中 上传到第三方问题
    Android控件属性大全(转)
    Android studio 一个项目中添加两个module遇到的bug
    win7 64位DCOM配置(关于导出excel 配置计算机组件服务)(转)
    Python学习--07迭代器、生成器
  • 原文地址:https://www.cnblogs.com/wyswyz/p/11788256.html
Copyright © 2011-2022 走看看