标签:define 技术分享 ext lcm inf def mod next ace
堆优化 dijkstra
int dis[N],vis[N]; struct Node{ int x,d; Node(){} Node(int _x,int _d){ x=_x,d=_d; } friend bool operator < (Node x,Node y){ return x.d>y.d; } }; priority_queue <Node> Q; void Dijkstra(){ while (!Q.empty()) Q.pop(); for (int i=1;i<=n;i++) dis[i]=2e9+5; dis[1]=0; memset(vis,0,sizeof vis); Q.push(Node(1,0)); while (!Q.empty()){ Node now=Q.top(); Q.pop(); int x=now.x; if (vis[x]) continue; vis[x]=1,dis[x]=now.d; for (int i=g.fst[x];i;i=g.nxt[i]) Q.push(Node(g.y[i],dis[x]+g.z[i])); } }
exgcd
int exgcd(int a,int b,int &x,int &y){ if (!b){ x=1,y=0; return a; } int res=exgcd(b,a%b,y,x); y-=(a/b)*x; return q; }
exkmp
#include <bits/stdc++.h> using namespace std; void exKMP(char s[],char t[],int g[],int f[],int n,int m){ int Max=0; f[0]=m; for (int i=1;i<m;i++){ f[i]=max(0,min(f[i-Max],Max+f[Max]-i)); while (i+f[i]<m&&t[f[i]]==t[i+f[i]]) f[i]++; if (!Max||i+f[i]>Max+f[Max]) Max=i; } Max=0; for (int i=0;i<n;i++){ g[i]=max(0,min(f[i-Max],Max+g[Max]-i)); while (i+g[i]<n&&t[g[i]]==s[i+g[i]]) g[i]++; if (!Max||i+g[i]>Max+g[Max]) Max=i; } } int main(){ return 0; }
FFT
#include <bits/stdc++.h> using namespace std; const int N=1<<20; const double PI=acos(-1.0); struct C{ double r,i; C(){} C(double a,double b){r=a,i=b;} C operator + (C x){return C(r+x.r,i+x.i);} C operator - (C x){return C(r-x.r,i-x.i);} C operator * (C x){return C(r*x.r-i*x.i,r*x.i+i*x.r);} }a[N],b[N],w[N]; int A,B,n,L,R[N]; void FFT(C a[],int n){ for (int i=0;i<n;i++) if (R[i]>i) swap(a[R[i]],a[i]); for (int t=n>>1,d=1;d<n;d<<=1,t>>=1) for (int i=0;i<n;i+=(d<<1)) for (int j=0;j<d;j++){ C tmp=w[t*j]*a[i+j+d]; a[i+j+d]=a[i+j]-tmp; a[i+j]=a[i+j]+tmp; } } int main(){ scanf("%d",&A);A++; scanf("%d",&B);B++; for (int i=0;i<A;i++) scanf("%lf",&a[i].r); for (int i=0;i<B;i++) scanf("%lf",&b[i].r); for (n=1,L=0;n<=A+B;n<<=1,L++); for (int i=0;i<n;i++){ R[i]=(R[i>>1]>>1)|((i&1)<<(L-1)); w[i]=C(cos(2.0*i*PI/n),sin(2.0*i*PI/n)); } FFT(a,n),FFT(b,n); for (int i=0;i<n;i++) a[i]=a[i]*b[i],w[i].i=-w[i].i; FFT(a,n); A--,B--; for (int i=0;i<=A+B;i++) printf("%d ",int(a[i].r/n+0.5)); return 0; }
NTT
#include <cstdio> #include <algorithm> #include <cstdlib> #include <cmath> #include <cstring> using namespace std; typedef long long LL; const LL mod=998244353; const int N=1<<20; LL Pow(LL x,LL y){ if (!y) return 1LL; LL xx=Pow(x,y/2); xx=xx*xx%mod; if (y&1LL) xx=xx*x%mod; return xx; } LL A,B,a[N],b[N],R[N],g[N],n,L; char str[N]; void read(){ scanf("%s",str); A=strlen(str); for (int i=0;i<A;i++) a[A-i-1]=str[i]-‘0‘; scanf("%s",str); B=strlen(str); for (int i=0;i<B;i++) b[B-i-1]=str[i]-‘0‘; } void NTT(LL a[N],int n){ for (int i=0;i<n;i++) if (i<R[i]) swap(a[i],a[R[i]]); for (int d=1,t=n>>1;d<n;d<<=1,t>>=1) for (int i=0;i<n;i+=(d<<1)) for (int j=0;j<d;j++){ LL tmp=g[t*j]*a[i+j+d]%mod; a[i+j+d]=(a[i+j]-tmp+mod)%mod; a[i+j]=(a[i+j]+tmp)%mod; } } int main(){ read(); for (n=1,L=0;n<=A+B;n<<=1,L++); for (int i=0;i<n;i++) R[i]=(R[i>>1]>>1)|((i&1)<<(L-1)); g[0]=1,g[1]=Pow(3,(mod-1)/n); for (int i=2;i<n;i++) g[i]=g[i-1]*g[1]%mod; NTT(a,n),NTT(b,n); for (int i=0;i<n;i++) a[i]=a[i]*b[i]%mod; g[0]=1,g[1]=Pow(g[1],mod-2); for (int i=2;i<n;i++) g[i]=g[i-1]*g[1]%mod; NTT(a,n); LL Inv=Pow(n,mod-2); for (int i=0;i<n;i++) a[i]=a[i]*Inv%mod; for (int i=0;i<n-1;i++) a[i+1]+=a[i]/10,a[i]%=10; int d; for (d=n-1;d&&!a[d];d--); for (int i=d;i>=0;i--) putchar(a[i]+‘0‘); return 0; }
KM
int ex[N],ey[N],minadd[N],match[N]; bool visx[N],visy[N]; bool Match(int x){ visx[x]=1; for (int i=1;i<=n;i++) if (!visy[i]){ int add=ex[x]+ey[i]-g[x][i]; if (!add){ visy[i]=1; if (!match[i]||Match(match[i])){ match[i]=x; return 1; } } else minadd[i]=min(minadd[i],add); } return 0; } int KM(){ memset(match,0,sizeof match); memset(ex,0,sizeof ex); memset(ey,0,sizeof ey); for (int i=1;i<=n;i++) for (int j=1;j<=n;j++) ex[i]=max(ex[i],g[i][j]); for (int i=1;i<=n;i++){ for (int j=1;j<=n;j++) minadd[j]=INF; while (1){ memset(visx,0,sizeof visx); memset(visy,0,sizeof visy); if (Match(i)) break; int d=INF; for (int j=1;j<=n;j++) if (!visy[j]) d=min(d,minadd[j]); for (int j=1;j<=n;j++){ if (visx[j]) ex[j]-=d; if (visy[j]) ey[j]+=d; else minadd[j]-=d; } } } int ans=0; for (int i=1;i<=n;i++) ans+=g[match[i]][i]; return ans; }
Manachar
char s[N],str[N]; void Manachar(){ for (int i=0;i<n;i++) str[i*2+1]=s[i+1]; for (int i=0;i<=n;i++) str[i*2]=‘%‘; int R=0,p=0; for (int i=1;i<n*2;i++){ r[i]=max(1,min(r[p*2-i],R-i)); while (i-r[i]>=0&&i+r[i]<=n*2&&str[i-r[i]]==str[i+r[i]]) r[i]++; if (i+r[i]>R) R=i+r[i],p=i; } }
Pollard_Rho (RXDoi)
#include<bits/stdc++.h> #define pb push_back using namespace std; typedef long long LL; typedef unsigned long long ULL; vector<LL> V; namespace Rho { int prime[9] = {2, 3, 5, 7, 11, 13, 17, 19, 23}; ULL RR; int Pcnt; LL p[70]; LL R(LL MOD) { return (RR += 4179340454199820289ll) % MOD; } LL mul(LL x, LL y, LL MOD){ LL tmp = (x * y - (LL)((long double)x / MOD * y + 0.5) * MOD); return tmp < 0 ? tmp + MOD : tmp; } //O(1)???�?1????http://blog.csdn.net/qq_35649707/article/details/76732760 LL Pow(LL x,LL k,LL MOD){ LL ans=1; for(; k; k>>=1,x=mul(x,x,MOD)) if (k&1) ans = mul(ans, x, MOD); return ans; } int MR(LL n){ if (n <= 1) return 0; for (int i=0; i<9; i++) if (n == prime[i]) return 1; LL d = n - 1; int tmp = 0; while ((d&1) == 0) d >>= 1, tmp++; for(int i=0; i<9; i++){ LL x = Pow(prime[i], d, n), p = x; for(int j=1; j<=tmp; j++){ x = mul(x,x,n); if (x == 1 && p != 1 && p != n-1) return 0; p = x; } if(x != 1)return 0; } return 1; } LL f(LL x,LL c,LL MOD){ return (mul(x, x, MOD) + c) % MOD;} LL gcd(LL x,LL y) { return !x ? y : gcd(y%x,x); } LL check(LL c,LL n){ LL x = R(n), y = f(x, c, n), p = n; while(x != y && (p == n || p == 1)){ if (x > y) p = gcd(n, x - y); else p = gcd(n, y - x); x = f(x, c, n); y = f(f(y, c, n), c, n); } return p; } void rho(LL n){ if (n <= 1) return; if (MR(n)) { V.pb(n); return; } while(true){ LL tmp = check(R(n - 1) + 1, n); if (tmp != n && tmp != 1) { rho(tmp), rho(n/tmp); return; } } } } int main() { LL n; scanf("%lld", &n); Rho::rho(n); printf("%lld\n", V.back()); return 0; }
SA (附带 ST 表查询区间 LCP )
int SA[N],rank[N],tmp[N],height[N],tax[N]; int ST[N][20]; void Sort(int n,int m){ for (int i=0;i<=m;i++) tax[i]=0; for (int i=1;i<=n;i++) tax[rank[i]]++; for (int i=1;i<=m;i++) tax[i]+=tax[i-1]; for (int i=n;i>=1;i--) SA[tax[rank[tmp[i]]]--]=tmp[i]; } bool cmp(int rk[],int x,int y,int w){ return rk[x]==rk[y]&&rk[x+w]==rk[y+w]; } void Suffix_Array(int s[],int n){ memset(SA,0,sizeof SA); memset(tmp,0,sizeof tmp); memset(rank,0,sizeof rank); memset(height,0,sizeof height); for (int i=1;i<=n;i++) rank[i]=s[i],tmp[i]=i; int m=234; Sort(n,m); for (int w=1,p=0;p<n;w<<=1,m=p){ p=0; for (int i=n-w+1;i<=n;i++) tmp[++p]=i; for (int i=1;i<=n;i++) if (SA[i]>w) tmp[++p]=SA[i]-w; Sort(n,m); swap(rank,tmp); rank[SA[1]]=p=1; for (int i=2;i<=n;i++) rank[SA[i]]=cmp(tmp,SA[i],SA[i-1],w)?p:++p; } for (int i=1,j,k=0;i<=n;height[rank[i++]]=k) for (k=max(k-1,0),j=SA[rank[i]-1];s[i+k]==s[j+k];k++); height[1]=0; } void Get_ST(int n){ memset(ST,0,sizeof ST); for (int i=1;i<=n;i++){ ST[i][0]=height[i]; for (int j=1;j<20;j++){ ST[i][j]=ST[i][j-1]; if (i-(1<<(j-1))>0) ST[i][j]=min(ST[i][j],ST[i-(1<<(j-1))][j-1]); } } } int Query(int L,int R){ int val=floor(log(R-L+1)/log(2)); return min(ST[L+(1<<val)-1][val],ST[R][val]); }
SAM (非广义)
#include <bits/stdc++.h> using namespace std; struct SAM{ int Next[26],fa,Max; }t[N<<1]; int size=1,root=1,last=1; void extend(int c){ int p=last,np=++size,q,nq; t[np].Max=t[p].Max+1; for (;p&&!t[p].Next[c];p=t[p].fa) t[p].Next[c]=np; if (!p) t[np].fa=root; else { q=t[p].Next[c]; if (t[q].Max==t[p].Max+1) t[np].fa=q; else { nq=++size; t[nq]=t[q],t[nq].Max=t[p].Max+1; t[q].fa=t[np].fa=nq; for (;p&&t[p].Next[c]==q;p=t[p].fa) t[p].Next[c]=nq; } } last=np; }
ISAP
#include <cstring> #include <cstdio> #include <cstdlib> #include <cmath> #include <algorithm> using namespace std; const int N=55005,M=N*3*2,INF=1e9; struct edge{ int x,y,cap,flow,nxt; }; struct gragh{ int cnt,fst[N],dist[N],n,S,T,num[N],cur[N],p[N]; int q[N],head,tail; edge e[M]; void set(int _S,int _T,int _n){ S=_S,T=_T,n=_n,cnt=1; memset(fst,0,sizeof fst); } void add(int a,int b,int c){ cnt++; e[cnt].x=a,e[cnt].y=b,e[cnt].cap=c,e[cnt].flow=0; e[cnt].nxt=fst[a],fst[a]=cnt; cnt++; e[cnt].x=b,e[cnt].y=a,e[cnt].cap=0,e[cnt].flow=0; e[cnt].nxt=fst[b],fst[b]=cnt; } void bfs(){ memset(dist,-1,sizeof dist); head=tail=dist[T]=0; q[++tail]=T; while (head<tail) for (int x=q[++head],y,i=fst[x];i;i=e[i].nxt) if ((i&1)&&dist[y=e[i].y]==-1) dist[q[++tail]=y]=dist[x]+1; for (int i=1;i<=n;i++) if (dist[i]==-1) dist[i]=n; } void init(){ bfs(); memset(num,0,sizeof num); for (int i=1;i<=n;i++) num[dist[i]]++,cur[i]=fst[i]; } int Augment(int &x){ int ex_flow=INF; for (int i=T;i!=S;i=e[p[i]].x) if (e[p[i]].cap-e[p[i]].flow<=ex_flow) ex_flow=e[p[i]].cap-e[p[i]].flow,x=e[p[i]].x; for (int i=T;i!=S;i=e[p[i]].x) e[p[i]].flow+=ex_flow,e[p[i]^1].flow-=ex_flow; return ex_flow; } int ISAP(){ int x=S,y,MaxFlow=0; init(); while (dist[S]<n){ if (x==T){ MaxFlow+=Augment(x); continue; } bool found=0; for (int i=cur[x];i;i=e[i].nxt) if (dist[y=e[i].y]+1==dist[x]&&e[i].cap>e[i].flow){ cur[x]=p[y]=i,x=y,found=1; break; } if (!found){ int d=n+1; for (int i=fst[x];i;i=e[i].nxt) if (e[i].cap>e[i].flow) d=min(d,dist[e[i].y]+1); if (!--num[dist[x]]) return MaxFlow; num[dist[x]=d]++,cur[x]=fst[x],x=x==S?x:e[p[x]].x; } } return MaxFlow; } }g;
SPFA 费用流
#include <cstring> #include <cstdio> #include <cmath> #include <cstdlib> #include <algorithm> using namespace std; const int N=85; struct edge{ int x,y,flow,cap,nxt,cost; }; struct gragh{ static const int N=85*85,M=N*N*2; int n,m,S,T,lim,fst[N],f[N],a[N],p[N],q[N],d[N]; edge e[M]; void init(int _n,int _lim){ n=_n,m=1,lim=_lim; memset(fst,0,sizeof fst); } void add(int a,int b,int cap,int cost){ m++; e[m].x=a,e[m].y=b,e[m].cap=cap,e[m].cost=cost,e[m].flow=0; e[m].nxt=fst[a],fst[a]=m; m++; e[m].x=b,e[m].y=a,e[m].cap=0,e[m].cost=-cost,e[m].flow=0; e[m].nxt=fst[b],fst[b]=m; } bool SPFA(int S,int T,int &flow,int &cost){ int head=0,tail=0,qmod=n+1,x,y; memset(f,0,sizeof f); for (int i=1;i<=n;i++) d[i]=1e9; d[S]=0,q[tail=tail%qmod+1]=S,a[S]=1e9; while (head!=tail){ f[x=q[head=head%qmod+1]]=0; for (int i=fst[x];i;i=e[i].nxt){ y=e[i].y; if (e[i].flow<e[i].cap&&d[x]+e[i].cost<d[y]){ d[y]=d[x]+e[i].cost; a[y]=min(a[x],e[i].cap-e[i].flow); p[y]=i; if (!f[y]) f[q[tail=tail%qmod+1]=y]=1; } } } if (d[T]>5e8) return 0; flow+=a[T],cost+=d[T]*a[T]; for (x=T;x!=S;x=e[p[x]].x) e[p[x]].flow+=a[T],e[p[x]^1].flow-=a[T]; return 1; } int MinCost(int S,int T){ int flow=0,cost=0; while (SPFA(S,T,flow,cost)); if (flow<lim) return -1; return cost; } }g;
Splay - BZOJ3224
#include <bits/stdc++.h> using namespace std; const int N=100005; int n,root=1,size=1,val[N],cnt[N],son[N][2],fa[N],tot[N]; int wson(int x){ return son[fa[x]][1]==x; } void pushup(int x){ tot[x]=cnt[x]+tot[son[x][0]]+tot[son[x][1]]; } void rotate(int x){ if (!x) return; int y=fa[x],z=fa[y],L=wson(x),R=L^1; if (z) son[z][wson(y)]=x; fa[x]=z,fa[y]=x,fa[son[x][R]]=y; son[y][L]=son[x][R],son[x][R]=y; pushup(y),pushup(x); } void splay(int x,int k){ if (!x) return; if (!k) root=x; for (int y=fa[x];fa[x]!=k;rotate(x),y=fa[x]) if (fa[y]!=k) rotate(wson(x)==wson(y)?y:x); } int find(int x,int v){ return val[x]==v?x:find(son[x][v>val[x]],v); } int findkth(int x,int k){ if (k<=tot[son[x][0]]) return findkth(son[x][0],k); k-=tot[son[x][0]]; if (k<=cnt[x]) return x; k-=cnt[x]; return findkth(son[x][1],k); } int findnxt(int x,int v){ if (!x) return 0; if (val[x]<=v) return findnxt(son[x][1],v); else { int res=findnxt(son[x][0],v); return res?res:x; } } int findpre(int x,int v){ if (!x) return 0; if (val[x]>=v) return findpre(son[x][0],v); else { int res=findpre(son[x][1],v); return res?res:x; } } void insert(int &x,int pre,int v){ if (!x){ x=++size; val[x]=v,cnt[x]=tot[x]=1,fa[x]=pre; splay(x,0); return; } tot[x]++; if (val[x]==v){ cnt[x]++; return; } insert(son[x][v>val[x]],x,v); } void Insert(int v){insert(root,0,v);} void Delete(int v){ int x; splay(x=find(root,v),0); if (--cnt[x]) return; splay(findnxt(root,v),root); root=son[x][1]; son[root][0]=son[x][0]; fa[son[x][0]]=root; fa[root]=son[x][0]=son[x][1]=0; pushup(root); } int Rank(int v){ splay(find(root,v),0); return tot[son[root][0]]+1; } int main(){ val[1]=2147483647; cnt[1]=tot[1]=1; scanf("%d",&n); while (n--){ int opt,x; scanf("%d%d",&opt,&x); if (opt==1) Insert(x); if (opt==2) Delete(x); if (opt==3) printf("%d\n",Rank(x)); if (opt==4) printf("%d\n",val[findkth(root,x)]); if (opt==5) printf("%d\n",val[findpre(root,x)]); if (opt==6) printf("%d\n",val[findnxt(root,x)]); } return 0; }
高精度整数运算 (由于懒和菜,没有更新带 FFT 的乘法和快速的除法)
支持负数
#include <cstring> #include <cstdio> #include <cstdlib> #include <algorithm> #include <cmath> #define max(a,b) ((a)>(b)?(a):(b)) #define min(a,b) ((a)<(b)?(a):(b)) using namespace std; typedef long long LL; /* 大数模板8 1. 支持大数之间的+、-、*、/、%运算,以及一些基础的计算 2. 支持部分大数与整型之间的运算 (仅限于大数在前整型在后) +、-、*、/、% 3. 支持负数的运算,不会出现减法的时候由于被减数小于减数所造成的报错。 4. 快速幂,代码优化 5. 可以进行正常的比较。 6. 新增 abs(), read()两个方便的函数 read() 具体用法 1. read(‘c‘,Var_Name<BigInt>) 读入一个char数组类型转化而来的大数 2. read(‘i‘,Var_Name<BigInt>) 读入一个int类型转化而来的大数 3. read(‘L‘,Var_Name<BigInt>) 读入一个long long类型转化而来的大数 7. 修复原先模板中关于0的bug 8. 新增构造函数 9. 修复若干bug,新增一些功能 10. progress: 9位压位,大大提高效率 *///版权所有--周镇东 const int MaxLen=1200; const LL mod=1e9; const LL Pow10[9]={1e0,1e1,1e2,1e3,1e4,1e5,1e6,1e7,1e8}; struct BigInt{ LL d,v[MaxLen+5]; bool f;//保存正负性 ,0当作正数看待 BigInt (){} BigInt (LL x){(*this)=x;} BigInt (int x){(*this)=x;} BigInt (char x[]){(*this)=x;} BigInt (const BigInt &x){(*this)=x;} void Print(){ if (f) putchar(‘-‘); if (d==0){ putchar(‘0‘); return; } printf("%lld",v[d]); for (int i=d-1;i>=1;i--) printf("%09lld",v[i]); } void Print(char c){//输出数字 (*this).Print(); printf("%c",c); } void ya(){ LL v_[MaxLen]; memset(v_,0,sizeof v_); for (int i=1;i<=d;i++) v_[(i-1)/9+1]+=Pow10[(i-1)%9]*v[i]; d=(d-1)/9+1; memset(v,0,sizeof v); for (int i=1;i<=d;i++) v[i]=v_[i]; while (d>0&&v[d]==0) d--; } void operator =(char x[]){ f=x[0]==‘-‘,d=strlen(x)-f,memset(v,0,sizeof v); for (int i=f;i<d+f;i++) v[i-f+1]+=(x[d+f-(i-f)-1]-48); while (d>0&&v[d]==0) d--; (*this).ya(); } void operator =(int x){ (*this)=(LL)x; } void operator =(LL x){ d=0,f=x<0,x=abs(x); memset(v,0,sizeof v); while (x) v[++d]=x%mod,x/=mod; } bool equ(BigInt &x){//cmp abs if (d!=x.d) return 0; for (int i=1;i<=d;i++) if (v[i]!=x.v[i]) return 0; return 1; } bool operator ==(BigInt &x){//cmp abs if (f!=x.f) return 0; return (*this).equ(x); } bool nequ(BigInt &x){ return !(*this).equ(x); } bool operator !=(BigInt &x){ return !(*this==x); } bool smaller(BigInt &x){ if (d!=x.d) return d<x.d; for (int i=d;i>=1;i--) if (v[i]!=x.v[i]) return v[i]<x.v[i]; return 0; } bool bigger(BigInt &x){ if (d!=x.d) return d>x.d; for (int i=d;i>=1;i--) if (v[i]!=x.v[i]) return v[i]>x.v[i]; return 0; } bool operator <(BigInt &x){//cmp abs if (f!=x.f) return f; if (f&&x.f) return (*this).bigger(x); return (*this).smaller(x); } bool operator >(BigInt &x){ if (f!=x.f) return x.f; if (f&&x.f) return (*this).smaller(x); return (*this).bigger(x); } bool smqu(BigInt &x){ return !(*this).bigger(x); } bool bgqu(BigInt &x){ return !(*this).smaller(x); } bool operator <=(BigInt &x){ return !(*this>x); } bool operator >=(BigInt &x){ return !(*this<x); } BigInt operator +(BigInt x){//加法运算 BigInt Ans=*this; if (f!=x.f){ Ans.f=x.f=0; if (f) return x-Ans; else return Ans-x; } memset(Ans.v,0,sizeof Ans.v); Ans.f=f,Ans.d=max(d,x.d); for (int i=1;i<=Ans.d;i++) Ans.v[i]=v[i]+x.v[i]; for (int i=1;i<=Ans.d;i++) Ans.v[i+1]+=Ans.v[i]/mod,Ans.v[i]%=mod; if (Ans.v[Ans.d+1]) Ans.d++; if (Ans.d==0) Ans.f=0; return Ans; } BigInt operator +(const LL x){ BigInt X(x); return X+(*this); } BigInt operator -(BigInt y){//减法运算 BigInt Ans=*this; if (f!=y.f){ y.f=Ans.f,Ans=Ans+y; return Ans; } if (Ans.equ(y)){ Ans=0; return Ans; } if (Ans.smaller(y)){ Ans=y-Ans,Ans.f=!f; return Ans; } for (int i=1;i<=max(Ans.d,y.d);i++) if (Ans.v[i]-y.v[i]<0) Ans.v[i]+=mod-y.v[i],Ans.v[i+1]--; else Ans.v[i]-=y.v[i]; while (Ans.d>0&&Ans.v[Ans.d]==0) Ans.d--; if (Ans.d==0) Ans.f=0; return Ans; } BigInt operator -(const LL x){ BigInt Ans(x); return (*this)-Ans; } BigInt operator *(const BigInt &y){//乘法运算 BigInt x=*this,Ans(0); Ans=0,Ans.f=f^y.f; for (int i=1;i<=x.d;i++) for (int j=1;j<=y.d;j++){ LL now=Ans.v[i+j-1]+x.v[i]*y.v[j]; Ans.v[i+j-1]=now%mod; Ans.v[i+j]+=now/mod; } Ans.d=x.d+y.d-1; for (int i=1;i<=Ans.d;i++) Ans.v[i+1]+=Ans.v[i]/mod,Ans.v[i]%=mod; if (Ans.v[Ans.d+1]) Ans.d++; if (Ans.d==0) Ans.f=0; return Ans; } BigInt operator *(LL y){ BigInt Ans=*this; if (y<0) Ans.f^=1; y=abs(y); for (int i=1;i<=d;i++) Ans.v[i]*=y; for (int i=1;i<=d||Ans.v[i]>0;i++) Ans.v[i+1]+=Ans.v[i]/mod,Ans.v[i]%=mod,Ans.d=max(d,i); if (Ans.d==0) Ans.f=0; return Ans; } BigInt operator /(BigInt y){//除法运算 BigInt Ans(0),x=*this,minus; bool Ansf=f^y.f; x.f=y.f=0,minus=y; while ((minus*10).smqu(x)) minus=minus*10; while (minus.bgqu(y)){ Ans=Ans*10; while (minus.smqu(x)) x=x-minus,Ans=Ans+1; minus=minus/10; } Ans.f=Ansf; if (Ans.d==0) Ans.f=0; return Ans; } BigInt operator /(LL x){ BigInt Ans(0); LL prev=0; Ans.f=f^(x<0),Ans.d=0,x=abs(x); for (int i=d;i>0;i--){ prev=prev*mod+v[i]; if (prev>=x) Ans.v[i]=prev/x,prev%=x,Ans.d=max(Ans.d,i); } if (Ans.d==0) Ans.f=0; return Ans; } BigInt operator %(BigInt y){//取模运算 BigInt x=*this,minus; bool xfz=f^y.f; x.f=y.f=0,minus=y; if (x<y){ x.f=xfz; return x; } while ((minus*10).smqu(x)) minus=minus*10; while (minus.bgqu(y)){ while (minus.smqu(x)) x=x-minus; minus=minus/10; } x.f=xfz; if (x.d==0) x.f=0; return x; } LL operator %(LL x){ LL prev=0; bool flag=f^(x<0); x=abs(x); for (int i=d;i>0;i--) prev=prev*mod+v[i],prev%=x; if (flag) prev=-prev; return prev; } BigInt operator ^(int x){ BigInt Ans; Ans=1; if (x==0) return Ans; Ans=*this^(x/2); Ans=Ans*Ans; if (x&1) Ans=Ans**this; return Ans; } }zero(0),one(1); BigInt GcdY(BigInt x,BigInt y){ return y!=zero?GcdY(y,x%y):x; } BigInt Gcd(BigInt x,BigInt y){ x.f=y.f=0; if (x==zero) return y; if (y==zero) return x; return GcdY(x,y); } BigInt LcmY(BigInt x,BigInt y){ return x/GcdY(x,y)*y; } BigInt Lcm(BigInt x,BigInt y){ x.f=y.f=0; if (x==zero) return y; if (y==zero) return x; return LcmY(x,y); } BigInt abs(BigInt x){ x.f=0; return x; } void read(char ch,BigInt &x){ if (ch==‘c‘){ char str[MaxLen]; scanf("%s",str),x=str; } if (ch==‘i‘){ int y; scanf("%d",&y),x=y; } if (ch==‘L‘){ LL y; scanf("%lld",&y),x=y; } } void readint(BigInt &x,int &ret){ scanf("%d",&ret),x=ret; } void readLL(BigInt &x,LL &ret){ scanf("%lld",&ret),x=ret; } int main(){ BigInt A,B; LL a,b; readLL(A,a),readLL(B,b); A.Print(‘ ‘); B.Print(‘ ‘); // read(‘c‘,A),read(‘c‘,B); A.Print(‘ ‘); B.Print(‘ ‘); printf("Gcd(A,B)=");Gcd(A,B).Print(‘\n‘); A.Print(‘ ‘); B.Print(‘ ‘); printf("Lcm(A,B)=");Lcm(A,B).Print(‘\n‘); A.Print(‘ ‘); B.Print(‘ ‘); printf("A*B=");(A*B).Print(‘\n‘); A.Print(‘ ‘); B.Print(‘ ‘); printf("A-B=");(A-B).Print(‘\n‘); A.Print(‘ ‘); B.Print(‘ ‘); printf("A+B=");(A+B).Print(‘\n‘); A.Print(‘ ‘); B.Print(‘ ‘); printf("A/B=");(A/B).Print(‘\n‘); A.Print(‘ ‘); B.Print(‘ ‘); // printf("A/b=");(A/b).Print(‘\n‘); A.Print(‘ ‘); B.Print(‘ ‘); // printf("A^b=");(A^b).Print(‘\n‘); A.Print(‘ ‘); B.Print(‘ ‘); // printf("A*b=");(A*b).Print(‘\n‘); A.Print(‘ ‘); B.Print(‘ ‘); // printf("A+b=");(A+b).Print(‘\n‘); A.Print(‘ ‘); B.Print(‘ ‘); // printf("A-b=");(A-b).Print(‘\n‘); A.Print(‘ ‘); B.Print(‘ ‘); // printf("A%b=");printf("%d\n",A%b); A.Print(‘ ‘); B.Print(‘ ‘); printf("A%B=");(A%B).Print(‘\n‘); A.Print(‘ ‘); B.Print(‘ ‘); printf("A<B?->");printf("%d\n",A<B); A.Print(‘ ‘); B.Print(‘ ‘); printf("A>B?->");printf("%d\n",A>B); A.Print(‘ ‘); B.Print(‘ ‘); printf("A<=B?->");printf("%d\n",A<=B); A.Print(‘ ‘); B.Print(‘ ‘); printf("A>=B?->");printf("%d\n",A>=B); A.Print(‘ ‘); B.Print(‘ ‘); printf("A==B?->");printf("%d\n",A==B); A.Print(‘ ‘); B.Print(‘ ‘); printf("A!=B?->");printf("%d\n",A!=B); A.Print(‘ ‘); B.Print(‘ ‘); printf("abs(A)=");abs(A).Print(‘\n‘); A.Print(‘ ‘); B.Print(‘ ‘); printf("abs(B)=");abs(B).Print(‘\n‘); A.Print(‘ ‘); B.Print(‘ ‘); printf("\n优先级判断:\n"); A.Print(‘ ‘); B.Print(‘ ‘); printf("A*B^2=");(A*B^2).Print(‘\n‘); A.Print(‘ ‘); B.Print(‘ ‘);//ans:A*B^2=(A*B)^2 printf("A/A*B=");(A/A*B).Print(‘\n‘); A.Print(‘ ‘); B.Print(‘ ‘);//ans:A/A*B=B return 0; }
高精度分数运算(基于上一份高精度整数运算)
struct BigDouble{ BigInt a,b; void Print(){ (*this).Smaller(); if (a==zero){ printf("0"); return; } if (b==one) a.Print(); else a.Print(‘/‘),b.Print(); } void Print(char ch){ (*this).Smaller(); if (a==zero){ printf("0%c",ch); return; } if (b==one) a.Print(ch); else a.Print(‘/‘),b.Print(ch); } void Smaller(){ if (a==zero||b==zero) return; // a.Print(‘\n‘);b.Print(‘\n‘); BigInt gcd=Gcd(a,b); // puts("Small achieve"); a=a/gcd,b=b/gcd; // puts("div adchive"); if (b.f) a.f^=1,b.f^=1; } void operator = (BigInt x){ a=x,b=one; } BigDouble operator * (BigDouble x){ BigDouble ans; ans.a=a*x.a,ans.b=b*x.b; ans.Smaller(); return ans; } BigDouble operator * (BigInt x){ BigDouble ans; ans.a=x*a,ans.b=b; ans.Smaller(); return ans; } BigDouble operator - (BigDouble x){ BigDouble ans; BigInt lcm=Lcm(b,x.b),tt=lcm/b,tx=lcm/x.b; // BigInt lcm=one,tt=one,tx=one; ans.b=lcm,ans.a=a*tt-x.a*tx; ans.Smaller(); return ans; } BigDouble operator / (BigInt x){ BigDouble ans; // b.Print(‘\n‘);x.Print(‘\n‘); ans.a=a,ans.b=b*x; // puts("still alive"); ans.Smaller(); return ans; } BigDouble operator / (BigDouble x){ BigDouble ans; ans.a=a*x.b,ans.b=b*x.a; ans.Smaller(); return ans; } }x[N];
标签:define 技术分享 ext lcm inf def mod next ace
原文地址:https://www.cnblogs.com/zhouzhendong/p/MoBan.html