Códigos prácticos comunes para competiciones de C ++ (2)

Los lectores pueden publicar comentarios y suplementos (marcaré el blog y el enlace del suplemento)

Página anterior: Códigos comunes y prácticos para competiciones de C ++

Tabla de contenido

Juicio ordinario primo

Máximo común divisor de dos números (MCD)

Función de Euler

Descomponer los factores primos (despojados de la función de Euler)

Número de nodos en el árbol enraizados en x (lista de adyacencia)

Euclides extendido

Convertir el número decimal a otro sistema

Calcule el número de combinaciones C (n, m)

Versión O (m)

Versión O (logmod)

Versión O (1)

Encuentra el elemento inverso de a y mod p

Número primo del tamiz

Angstrom (O (nlnn))

Ou tamiz (O (n))


Más códigos de teoría de números de bajo nivel : https://blog.csdn.net/qq_41814502/article/details/88121632

Siguiente: Códigos prácticos comunes para competiciones de C ++ (3)

Juicio ordinario primo

inline bool is_prime(int n){
    if(n==1||n==0)return 0;
    for(int i=2;i*i<=n;i++)
        if(n%i==0)return 0;
    return 1;
}

Máximo común divisor de dos números (MCD)

#define ll long long
inline ll gcd(ll a,ll b){return b==0?a:gcd(b,a%b);}

Función de Euler

inline int phi(int a){//a的欧拉函数值:小于a且与a互质的数的个数
    int s=a;
    for(int o=2;o*o<=a;o++)
        if(a%o==0){
            s=s/o*(o-1);
            while(a%o==0)a/=o;
        }
    if(a>1)s=s/a*(a-1);
    return s;
}

Descomponer los factores primos (despojados de la función de Euler)

inline void prime_work(int a){
    for(int o=2;o*o<=a;o++)
        if(a%o==0){
            prime[++len]=o;
            while(a%o==0)num[len]++,a/=o;
        }
    if(a>1)prime[++len]=x,num[len]=1;
}

Número de nodos en el árbol enraizados en x (lista de adyacencia)

//普通:
int dfs(int x){
    int u=G[x].size(),Sum=1;
    for(int i=0;i<u;i++)
        Sum+=dfs(G[x][i]);
    return Sum;
}
//记忆化(用a数组保存):
int dfs(int x){
    if(a[x])return a[x];
    a[x]=1;
    int u=G[x].size();
    for(int i=0;i<u;i++)
        a[x]+=dfs(G[x][i]);
    return a[x];
}

Euclides extendido

int exgcd(int a,int b,int&x,int&y){
	int d;
	if(b==0){x=1,y=0;return a;}
	d=exgcd(b,a%b,y,x);
	y-=(a/b)*x;
	return d;
}

Convertir el número decimal a otro sistema

//将十进制x转换为d进制并输出
void Ten(int x,int d)//2≤d≤10
{
	int i,n=0,h=1;
	int s[32]={0};//可以换成全局数组保存结果
	if(x<0)
	{
		x*=-1;
		h=-1;
	}
	while(x>=d)
	{
		s[n++]=x%d;
		x/=d;
	}
	s[n]=x;
	if(h==-1)
		putchar('-');
	for(i=n;i>=0;i--)
		putchar(s[i]+'0');
}

Calcule el número de combinaciones C (n, m)

Versión O (m)

inline int C(int n,int m){
    int k=1;
    if(m<n){
        if(m<n-1)
            for(int i=1,j=n-m+1;i<=m;i++,j++)
                k=k*j/i;
        else k=n;
    }
    return k;
}

Versión O (logmod)

#define ll long long
inline ll ksm(ll a,ll b){//快速幂
    ll res=1;
    for(;b;b>>=1){
        if(b&1)res=res*a%mod;
        a=a*a%mod;
    }
    return res;
}
inline void prepare(){
    jc[0]=jc[1]=1;
    for(int i=2;i<=MAXN;i++)jc[i]=jc[i-1]*i%mod;
}
inline ll C(int n,int m){//阶乘数组jc要预处理↑
	if(m>n)return 0;
	return jc[n]*ksm(jc[m],mod-2)%mod*ksm(jc[n-m],mod-2)%mod;
}//前提是mod得是个质数(一般给的都是1e9+7)

Versión O (1)

1. ( Estructura de puntuación combinada )

#define ll long long
inline void prepare(){//阶乘预处理 
    jc[0]=jc[1]=1;
    for(int i=2;i<=MAXN;i++)jc[i]=jc[i-1]*i%mod;
}
inline ll C(ll n,ll m){
	if(m>n)return 0;
	return Q(jc[n],jc[m]*jc[n-m]%mod);
}

2. Preprocesamiento del elemento inverso

#define ll long long
inline ll ksm(ll a,ll b){
	ll res=1;
	for(;b;b>>=1){
		if(b&1)res=res*a%mod;
		a=a*a%mod;
	}
	return res;
}
inline void prepare(){//阶乘、逆元预处理,inv[i]表示i!的逆元
	fac[0]=fac[1]=inv[0]=1;
	for(int i=2;i<=MAXN;i++)fac[i]=fac[i-1]*i%mod;
	inv[MAXN]=ksm(fac[MAXN],mod-2);
	for(int i=MAXN-1;i>0;i--)inv[i]=inv[i+1]*(i+1)%mod;
}
inline ll C(int n,int m){
	if(m>n)return 0;
	return fac[n]*inv[m]%mod*inv[n-m]%mod;
}

Encuentra el elemento inverso de a y mod p

inline int niyuan(int a,int p){
	int phi=p,x=p;//欧拉函数begin
	for(int i=2;i<=x;i++)
		if(x%i==0){phi-=phi/i;while(x%i==0)x/=i;}
	if(x>1)phi-=phi/x;//欧拉函数end
	phi--;
	int ans=1;//快速幂begin
    for(;phi;phi>>=1){
		if(phi&1)ans=ans*a%p;
		a=a*a%p;
	}//快速幂end
	return ans;
}

Número primo del tamiz

Angstrom (O (nlnn))

//bool nop[MAXN+5];
nop[0]=nop[1]=1;
for(int i=2;i<=MAXN;i++)
	if(!nop[i])
		for(int j=(i<<1);j<=MAXN;j+=i)
			nop[j]=1;

Ou tamiz (O (n))

//bool nop[MAXN+5];
//vector<int>pr;
nop[0]=nop[1]=1;
for(int a=2;a<=MAXN;a++){
	if(!nop[a])pr.push_back(a);
	for(int i=0;i<pr.size();i++){
		if(pr[i]*a>MAXN)break;
		nop[a*pr[i]]=1;
		if(a%pr[i]==0)break;
	}
}

Los lectores pueden publicar comentarios y suplementos ~

Supongo que te gusta

Origin blog.csdn.net/weixin_43960287/article/details/87555268
Recomendado
Clasificación