板子
来源:互联网 发布:淘宝云客服哪个部门好 编辑:程序博客网 时间:2024/04/28 01:11
基本
快读
inline void read(int &n){ n=0;bool b=0; char c=getchar(); while(c<'0'||c>'9'){c=getchar();if(c=='-')b=1;} while(c>='0'&&c<='9') n=n*10+c-48,c=getchar(); if(b) n=-n;}
图论
tarjan
//强连通分量void dfs(int now,int fa){ dfn[now]=low[now]=++Time; instack[now]=1; s.push(now); for(int i=head[now];i;i=a[i].nxt) if(!dfn[a[i].to]) { dfs(a[i].to,now); low[now]=min(low[now],low[a[i].to]); } else if(instack[a[i].to]) low[now]=min(low[now],dfn[a[i].to]); if(dfn[now]==low[now]) { tot++; int tmp; do { tmp=s.top(); instack[tmp]=0; }while(tmp!=now); }}//缩点void dfs(int now){ low[now]=dfn[now]=++Time; s[++top]=now; instack[now]=1; for(int i=head[now];i;i=a[i].nxt) if(!dfn[a[i].to]) { dfs(a[i].to); low[now]=min(low[now],low[a[i].to]); } else if(instack[a[i].to]) low[now]=min(low[now],dfn[a[i].to]); if(low[now]==dfn[now]) { int tmp; tot++; do { tmp=s[top--]; instack[tmp]=0; block[tmp]=tot; size[tot]++; }while(tmp!=now); }}//LCAint find(int n){ if(f[n]!=n) f[n]=find(f[n]); return f[n];}void dfs(int now,int depth){ f[now]=now; vis[now]=1; deep[now]=depth; for(int i=head[now];i;i=a[i].nxt) if(!vis[a[i].to]) { dfs(a[i].to,depth+a[i].dis); f[a[i].to]=now; } for(int i=Head[now];i;i=ask[i].nxt) if(vis[ask[i].to]) ans[ask[i].id]=deep[now]+deep[ask[i].to]-(deep[find(ask[i].to)]<<1);}
求RMQ
//h==0:取[l,r]的最大值h==1:取[l,r]的最小值 #include<cstdio>#include<cmath>#include<cstring>#define max(a,b) a>b?a:b#define min(a,b) a<b?a:bint n,i,j,l,r,x,h;int a[10001];int f[10001][15];int ff[10001][15];int main(){ scanf("%d",&n); for(i=1;i<=n;i++) scanf("%d",&a[i]); memset(ff,10,sizeof(ff)); for(i=1;i<=n;i++) { f[i][0]=a[i]; ff[i][0]=a[i]; } for(j=1;j<=log(n)/log(2);j++) for(i=1;i<=n+1-(1<<j);i++) { f[i][j]=max(f[i][j-1],f[i+(1<<(j-1))][j-1]); ff[i][j]=min(ff[i][j-1],ff[i+(1<<(j-1))][j-1]); } scanf("%d",&n); for(i=1;i<=n;i++) { scanf("%d%d%d",&h,&l,&r); x=log(r-l+1)/log(2); if(h==0) printf("%d\n",max(f[l][x],f[r+1-(1<<x)][x])); else printf("%d\n",min(ff[l][x],ff[r+1-(1<<x)][x])); } return 0;}
网络流
inline bool bfs(int s,int t){ memset(deep,0,sizeof(deep)); q.clear(); q.push(s); deep[s]=1; while(!q.empty()) { int tmp=q.front(); q.pop(); for(int i=head[tmp];i;i=a[i].next) if(a[i].remain&&!deep[a[i].to]) deep[a[i].to]=deep[tmp]+1,q.push(a[i].to); } return deep[t];}int dfs(int now,int t,int limit){ if(now==t) return limit; int flow=0,f; for(int i=head[now];i;i=a[i].next) if(a[i].remain&&deep[a[i].to]==deep[now]+1) { f=dfs(a[i].to,t,min(a[i].remain,limit)); a[i].remain-=f; a[i^1].remain+=f; limit-=f; flow+=f; if(!limit) return flow; } deep[now]=-1; return flow;}inline int dinic(int s,int t){ int ans=0; while(bfs(s,t)) ans+=dfs(s,t,INF); return ans;}
费用流
inline bool SPFA(){ memset(dis,10,sizeof(dis)); dis[S]=0; u[S]=INF; q.push(S),b[S]=1; while(!q.empty()) { int tmp=q.front();q.pop(); for(int i=head[tmp];i;i=a[i].next) if(dis[a[i].to]>dis[tmp]+a[i].cost&&a[i].remain) { f[a[i].to]=tmp; u[a[i].to]=min(u[tmp],a[i].remain); dis[a[i].to]=dis[tmp]+a[i].cost; if(!b[a[i].to]) q.push(a[i].to),b[a[i].to]=1; } } if(dis[T]>INF) return 0; ll p=T; while(p!=S) { a[f[p]].remain-=u[T]; a[f[p]^1].remain+=u[T]; p=a[f[p]^1].to; } ans+=u[T]*dis[T]; return 1;}inline void mcmf(){while(SPFA());}
莫队
#include<bits/stdc++.h>using namespace std;struct node{ int l,r,id;}q[200010];int a[50010];int ans[200010];int pos[200010];int num[1000010];int size,n,m,L=1,R,Ans;inline bool cmp(node a,node b){ if(pos[a.l]==pos[b.l]) return a.r<b.r; return pos[a.l]<pos[b.l];}int main(){ scanf("%d",&n); size=sqrt(n); for(int i=1;i<=n;i++) scanf("%d",&a[i]),pos[i]=i/size; scanf("%d",&m); for(int i=1;i<=m;i++) { scanf("%d%d",&q[i].l,&q[i].r); q[i].id=i; } sort(q+1,q+m+1,cmp); for(int i=1;i<=m;i++) { while(L<q[i].l) if(!--num[a[L++]]) Ans--; while(L>q[i].l) if(!num[a[--L]]++) Ans++; while(R<q[i].r) if(!num[a[++R]]++) Ans++; while(R>q[i].r) if(!--num[a[R--]]) Ans--; ans[q[i].id]=Ans; } for(int i=1;i<=m;i++) printf("%d\n",ans[i]); return 0;}
分块
#include<cmath>#include<cstdio>#include<algorithm>using namespace std;const int N=1e6+10;struct Block{ int l,r,num,plus; int a[1010]; inline void keep() { sort(a+1,a+num+1); } inline int find(int n) { int L=1,R=num,mid; n-=plus; while(L<R) { mid=(L+R)>>1; if(a[mid]<n) L=mid+1; else R=mid; } return L; }}a[1010];int s[N];int belong[N];int n,q,x,y,z,ans,block,num;char c;inline void read(int &n){ n=0;char c=getchar(); while(c<'0'||c>'9') c=getchar(); while(c>='0'&&c<='9') n=n*10+c-48,c=getchar();}inline void build(){ block=sqrt(n); num=n/block;if(n%block) num++; for(int i=1;i<=num;i++) a[i].l=(i-1)*block+1,a[i].r=i*block,a[i].num=block; a[num].r=n;a[num].num=a[num].r-a[num].l+1; for(int i=1;i<=n;i++) belong[i]=(i-1)/block+1; for(int i=1;i<=num;i++) { for(int j=a[i].l;j<=a[i].r;j++) a[i].a[j-a[i].l+1]=s[j]; a[i].keep(); }}inline void add(int x,int y,int z){ if(belong[x]==belong[y]) { for(int i=x;i<=y;i++) s[i]+=z; for(int i=a[belong[x]].l;i<=a[belong[x]].r;i++) a[belong[x]].a[i-a[belong[x]].l+1]=s[i]; a[belong[x]].keep(); return; } for(int i=x;i<=a[belong[x]].r;i++) s[i]+=z; for(int i=a[belong[x]].l;i<=a[belong[x]].r;i++) a[belong[x]].a[i-a[belong[x]].l+1]=s[i]; a[belong[x]].keep(); for(int i=belong[x]+1;i<belong[y];i++) a[i].plus+=z; for(int i=a[belong[y]].l;i<=y;i++) s[i]+=z; for(int i=a[belong[y]].l;i<=a[belong[y]].r;i++) a[belong[y]].a[i-a[belong[y]].l+1]=s[i]; a[belong[y]].keep();}inline int ask(int x,int y,int z){ int ans=0; if(belong[x]==belong[y]) { for(int i=x;i<=y;i++) if(s[i]+a[belong[x]].plus>=z) ans++; return ans; } for(int i=x;i<=a[belong[x]].r;i++) if(s[i]+a[belong[x]].plus>=z) ans++; for(int i=belong[x]+1;i<belong[y];i++) { int p=a[i].find(z); if(a[i].a[p]+a[i].plus>=z) ans+=a[i].num-p+1; } for(int i=a[belong[y]].l;i<=y;i++) if(s[i]+a[belong[y]].plus>=z) ans++; return ans;}int main(){ read(n),read(q); for(int i=1;i<=n;i++) read(s[i]); build(); while(q--) { c=getchar(); while(c!='A'&&c!='M') c=getchar(); read(x),read(y),read(z); if(c=='A') printf("%d\n",ask(x,y,z)); else add(x,y,z); } return 0;}
数论
Lucas&中国剩余定理&快速幂&扩展欧几里得&逆元
#include<cmath>#include<cstdio>typedef long long ll;const ll M=999911659;ll prime[5]={0,2,3,4679,35617};ll fac[40000];ll inv[40000];ll a[5];ll n,g,ans,x,y;inline ll pow(ll a,ll b,ll p){ ll ans=1; a%=p; for(;b;b>>=1,a=1ll*a*a%p) if(b&1) ans=1ll*ans*a%p; return ans;}void exgcd(ll a,ll b,ll &x,ll &y){ if(!b) {x=1,y=0;return;} exgcd(b,a%b,y,x); y-=(a/b)*x;}inline ll lucas(ll n,ll m,ll p){ ll ans=1; while(n&&m) { ll a=n%p,b=m%p; if(a<b) return 0; ans=(1ll*ans*fac[a]*inv[fac[b]]*inv[fac[a-b]])%p; n/=p,m/=p; } return ans;}int main(){ scanf("%lld%lld",&n,&g); inv[0]=1;fac[0]=1;fac[1]=1; for(ll i=1;i<=4;i++) { for(ll j=1;j<=prime[i];j++) { fac[j]=(fac[j-1]*j)%prime[i]; inv[j]=pow(j,prime[i]-2,prime[i]); } for(ll j=1;j<=sqrt(n);j++) if(!(n%j)) { a[i]=(1ll*a[i]+lucas(n,j,prime[i]))%prime[i]; if(j*j<n) a[i]=(1ll*a[i]+lucas(n,n/j,prime[i]))%prime[i]; } } for(ll i=1;i<=4;i++) { exgcd((M-1)/prime[i],prime[i],x,y); ans=(1ll*ans+1ll*a[i]*x*((M-1)/prime[i]))%(M-1); } ans=(ans%(M-1)+M-1)%(M-1); if(!ans) ans=M-1; printf("%lld",pow(g,ans,M)); return 0;}
扩展中国剩余定理
void exgcd(ll a,ll b,ll &x,ll &y){ if(!b){x=1,y=0;return;} exgcd(b,a%b,y,x); y-=(a/b)*x;}inline ll gcd(ll a,ll b){return !b?a:gcd(b,a%b);}inline ll inv(ll x,ll y){ ll x1,y1;exgcd(x,y,x1,y1); return (x1%y+y)%y;}inline bool merge(ll m1,ll r1,ll m2,ll r2,ll &m3,ll &r3){ ll d=gcd(m1,m2),r=r2-r1; if(r%d) return 0; r=(r%m2+m2)%m2; m1/=d,m2/=d; r=r/d*inv(m1,m2)%m2*m1*d+r1; m3=m1*m2*d,r3=(r%m3+m3)%m3; return 1;}inline ll CRT(){ ll m1=m[1],r1=r[1]; for(int i=2;i<=n;i++) { ll m2=m[i],r2=r[i],m3,r3; if(!merge(m1,r1,m2,r2,m3,r3)) return -1; m1=m3,r1=r3; } return (r1%m1+m1)%m1;}
欧拉定理
线性求phi
inline void calc(){ for(int i=1;i<n;i++) phi[i]=i; for(int i=2;i<n;i++) { if(phi[i]==i) for(int j=i;j<n;j+=i) phi[j]=(phi[j]/i)*(i-1); ans+=phi[i]; } ans++;}
单点求phi
inline ll phi(ll N){ ll ans=N; for(int i=2;i<=n;i++) if(N%i==0) { ans=ans/i*(i-1); while(N%i==0) N/=i; } if(N>1) ans=ans/N*(N-1); return ans;}
线性求逆元
inv[i]=1ll*(m-m/i)*inv[m%i]%m;
mobius反演&&(线性求mu值)
inline void mobius(){ mu[1]=1; for(int i=2;i<=100000;i++) { if(!Prime[i]) prime[++tot]=i,mu[i]=-1; for(int j=1;j<=tot&&prime[j]*i<=100000;j++) { Prime[prime[j]*i]=1; if(i%prime[j]==0) break; mu[prime[j]*i]=-mu[i]; } } for(int i=1;i<=100000;i++) { f[i].second=i; for(int j=i;j<=100000;j+=i) f[j].first+=i; } sort(f+1,f+100001);}inline void add(int pos,int num){ for(int i=pos;i<=100000;i+=lowbit(i)) a[i]+=num;}inline int ask(int pos){ int ans=0; for(int i=pos;i;i-=lowbit(i)) ans+=a[i]; return ans;}inline int solve(int n,int m){ if(n>m) swap(n,m); int ans=0; for(int i=1,last;i<=n;i=last+1) { last=min(n/(n/i),m/(m/i)); ans+=(ask(last)-ask(i-1))*(n/i)*(m/i); } return ans;}
高斯消元
for(int i=1;i<=n;i++) { int p=i; for(int j=i+1;j<=n;j++) if(fabs(f[j][i])>fabs(f[p][i])) p=j; if(p!=i) for(int j=1;j<=n+1;j++) swap(f[i][j],f[p][j]); double tmp=f[i][i]; for(int j=1;j<=n+1;j++) f[i][j]/=tmp; for(int k=1;k<=n;k++) if(k!=i) { tmp=f[k][i]; for(int j=1;j<=n+1;j++) f[k][j]-=f[i][j]*tmp; } }
FFT
typedef complex<double> cp;const double pi=acos(-1);inline void FFT(cp *a,int f){ for(int i=0;i<n;i++) if(i<r[i]) swap(a[i],a[r[i]]); for(int i=1;i<n;i<<=1) { cp wn(cos(pi/i),f*sin(pi/i)); for(int j=0,tmp=i<<1;j<n;j+=tmp) { cp w(1,0); for(int k=0;k<i;k++,w*=wn) { cp x=a[j+k],y=w*a[j+k+i]; a[j+k]=x+y,a[j+k+i]=x-y; } } }}
bsgs
inline ll bsgs(ll x,ll z,ll p){ ma.clear(),x%=p; if(!x&&!z) return 0; if(!x) return -1; ll m=(ll)ceil(sqrt((double)p)),tmp=1; ma[1]=m+1; for(int i=1;i<m;i++) { tmp=tmp*x%p; if(!ma[tmp]) ma[tmp]=i; } ll inv=1;tmp=ksm(x,p-m-1,p); for(ll k=0;k<m;k++) { int i=ma[(z*inv)%p]; if(i) { if(i==m+1) i=0; return k*m+i; } inv=(inv*tmp)%p; } return -1;}
字符串
AC自动机
struct AC{ int ch[26]; int fail,cnt;}a[500001];int n,m,tot;char s[1000001];inline void init(){ q.clear(); for(int i=0;i<=tot;i++) { memset(a[i].ch,0,sizeof(a[i].ch)); a[i].cnt=a[i].fail=0; } tot=0; a[0].fail=-1;}inline void insert(char *s){ int now=0,p,len=strlen(s); for(int i=0;i<len;i++) { p=s[i]-'a'; if(!a[now].ch[p]) a[now].ch[p]=++tot; now=a[now].ch[p]; } a[now].cnt++;}inline void makefail(){ q.push(0); while(!q.empty()) { int now=q.front(); q.pop(); for(int i=0;i<26;i++) if(a[now].ch[i]) { int p=a[now].fail; while(p!=-1&&!a[p].ch[i]) p=a[p].fail; if(p==-1) a[a[now].ch[i]].fail=0; else a[a[now].ch[i]].fail=a[p].ch[i]; q.push(a[now].ch[i]); } }}inline int find(int now){ int ans=0; while(now&&a[now].cnt!=-1) { ans+=a[now].cnt; a[now].cnt=-1; now=a[now].fail; } return ans;}inline int ask(char *s){ int ans=0,now=0,len=strlen(s); for(int i=0;i<len;i++) { int p=s[i]-'a'; if(a[now].ch[p]) now=a[now].ch[p]; else { int pos=a[now].fail; while(pos!=-1&&!a[pos].ch[p]) pos=a[pos].fail; if(pos==-1) now=0; else now=a[pos].ch[p]; } ans+=find(now); } return ans;}
Fail树
#include<queue>#include<cstdio>#include<cstring>#include<algorithm>using namespace std;#define lowbit(x) x&(-x)const int N=1e5+10;struct AC{ int ch[26]; int fail,fa;}a[N];struct query{ int x,y,id; bool operator <(const query other)const { return y<other.y; }}q[N];struct edge{ int next,to;}e[N<<1];int t[N],head[N],pos[N];char s[N];int in[N],out[N];int ans[N];int tot,num,n,x,y,Tot,len;inline void add(int x,int y){ e[++num].next=head[x],e[num].to=y,head[x]=num; e[++num].next=head[y],e[num].to=x,head[y]=num;}inline void build(){ int now=0,num=0; for(int i=0;i<len;i++) if(s[i]=='B') now=a[now].fa; else if(s[i]=='P') pos[++num]=now; else { if(!a[now].ch[s[i]-'a']) a[now].ch[s[i]-'a']=++tot,a[a[now].ch[s[i]-'a']].fa=now; now=a[now].ch[s[i]-'a']; }}inline void makefail(){ a[0].fail=-1; queue<int>Q; while(!Q.empty()) Q.pop(); for(int i=0;i<26;i++) if(a[0].ch[i]) { Q.push(a[0].ch[i]); add(0,a[0].ch[i]); } while(!Q.empty()) { int tmp=Q.front();Q.pop(); for(int i=0;i<26;i++) { if(!a[tmp].ch[i]) { a[tmp].ch[i]=a[a[tmp].fail].ch[i]; continue; } a[a[tmp].ch[i]].fail=a[a[tmp].fail].ch[i]; add(a[a[tmp].fail].ch[i],a[tmp].ch[i]); Q.push(a[tmp].ch[i]); } }}void dfs(int now,int fa){ in[now]=++Tot; for(int i=head[now];i;i=e[i].next) if(e[i].to!=fa) dfs(e[i].to,now); out[now]=Tot;}inline void Add(int now,int num){ for(int i=now;i<=Tot;i+=lowbit(i)) t[i]+=num;}inline int ask(int now){ int ans=0; for(int i=now;i;i-=lowbit(i)) ans+=t[i]; return ans;}inline void work(){ int now=0,tot=0,j=1; for(int i=0;i<len;i++) if(s[i]>='a'&&s[i]<='z') { now=a[now].ch[s[i]-'a']; Add(in[now],1); } else if(s[i]=='B') { Add(in[now],-1); now=a[now].fa; } else { tot++; for(;q[j].y==tot;j++) ans[q[j].id]=ask(out[pos[q[j].x]])-ask(in[pos[q[j].x]]-1); }}int main(){ scanf("%s",s); len=strlen(s); build(); makefail(); scanf("%d",&n); for(int i=1;i<=n;i++) scanf("%d %d",&q[i].x,&q[i].y),q[i].id=i; sort(q+1,q+n+1); dfs(0,-1); work(); for(int i=1;i<=n;i++) printf("%d\n",ans[i]); return 0;}
后缀数组
inline void makesa(){ int *x=t1,*y=t2,m=30; for(int i=0;i<m;i++) c[i]=0; for(int i=0;i<n;i++) c[x[i]=s[i]-'a']++; for(int i=1;i<m;i++) c[i]+=c[i-1]; for(int i=n-1;i>=0;i--) sa[--c[x[i]]]=i; for(int k=1;k<=n;k<<=1) { int p=0; for(int i=n-k;i<n;i++) y[p++]=i; for(int i=0;i<n;i++) if(sa[i]>=k) y[p++]=sa[i]-k; for(int i=0;i<m;i++) c[i]=0; for(int i=0;i<n;i++) c[x[y[i]]]++; for(int i=1;i<m;i++) c[i]+=c[i-1]; for(int i=n-1;i>=0;i--) sa[--c[x[y[i]]]]=y[i]; swap(x,y); p=1;x[sa[0]]=0; for(int i=1;i<n;i++) x[sa[i]]=cmp(y,sa[i],sa[i-1],k)?p-1:p++; if(p>=n) break; m=p; }}inline void makeheight(){ for(int i=0;i<n;i++) rank[sa[i]]=i; int k=0; for(int i=0;i<n;i++) if(rank[i]) { int j=sa[rank[i]-1]; if(k) k--; while(s[i+k]==s[j+k]) k++; height[rank[i]]=k; }}
manacher
scanf("%d\n",&n); a[0]='$'; for(int i=1;i<=n;i++) a[++len]='#',a[++len]=getchar(); a[len+1]=a[len+2]='#'; for(int i=1;i<=len;i++) { if(i<mx) p[i]=min(p[pos*2-i],mx-i); else p[i]=1; while(a[i-p[i]]==a[i+p[i]]) p[i]++; if(i+p[i]>mx) mx=i+p[i],pos=i; } for(int i=1;i<=len;i++) if(a[i]=='#') f[i]=i; else f[i]=i+1; for(int i=3;i<=len;i+=2) { int tmp=i-(p[i]>>1); if(!tmp) continue; tmp=find(tmp); while(tmp+p[tmp]<i&&tmp<i) f[tmp]=find(tmp+1),tmp=f[tmp]; if(tmp<i) ans=max(ans,(i-tmp)<<1); }
KMP
scanf("%s%s",a+1,b+1); l1=strlen(a+1),l2=strlen(b+1); j=0; for(i=2;i<=l2;i++) { while(j&&b[i]!=b[j+1]) j=next[j]; if(b[i]==b[j+1]) j++; next[i]=j; } j=0; for(i=1;i<=l1;i++) { while(j&&a[i]!=b[j+1]) j=next[j]; if(a[i]==b[j+1]) j++; if(j==l2) { printf("%d\n",i-l2+1); j=next[j]; } }
数据结构
LCT
#include<bits/stdc++.h>using namespace std;struct node{ int rev; node *ch[2],*fa; inline int getwh() { return fa->ch[0]==this?0:1; } inline void setch(int wh,node *child); inline bool isroot(); inline void pushdown() { if(rev) { node *t=ch[0];ch[0]=ch[1];ch[1]=t; ch[0]->rev^=1,ch[1]->rev^=1; rev=0; } }}pool[20001],*null;inline void node::setch(int wh,node *child){ ch[wh]=child; if(child!=null) child->fa=this;}inline bool node::isroot(){ return (fa==null)||(fa->ch[0]!=this&&fa->ch[1]!=this);}char s[10];int n,m,x,y;inline void getstring(){ int p=-1;char c=getchar(); while((c<'a'||c>'z')&&(c<'A'||c>'Z')) c=getchar(); while((c>='a'&&c<='z')||(c>='A'&&c<='Z')) s[++p]=c,c=getchar();}inline void clear(node *now){ now->fa=now->ch[0]=now->ch[1]=null;}inline void rotate(node *now){ node *fa=now->fa,*grand=now->fa->fa; if(!fa->isroot()) grand->pushdown(); fa->pushdown();now->pushdown(); int wh=now->getwh(); fa->setch(wh,now->ch[wh^1]); if(fa->isroot()) now->fa=fa->fa; else grand->setch(fa->getwh(),now); now->setch(wh^1,fa);}inline void splay(node *now){ if(now->isroot()) return; for(;!now->isroot();rotate(now)) if(!now->fa->isroot()) now->getwh()==now->fa->getwh()?rotate(now->fa):rotate(now);}inline node *access(node *now){ node *t=null; for(;now!=null;t=now,now=now->fa) splay(now),now->pushdown(),now->setch(1,t); return t;}inline void changeroot(node *now){ access(now)->rev^=1; splay(now);}inline void connect(node *x,node *y){ changeroot(x); x->fa=y; access(x);}inline void del(node *x,node *y){ changeroot(x); access(y); splay(x); x->pushdown(); x->ch[1]=y->fa=null;}inline node *findroot(node *now){ for(now=access(now);now->ch[0]!=null;now->pushdown(),now=now->ch[0]); return now;}inline bool ask(node *x,node *y){ if(findroot(x)==findroot(y)) return 1; return 0;}int main(){ null=pool; null->fa=null->ch[0]=null->ch[1]=null; scanf("%d%d",&n,&m); for(int i=1;i<=n;i++) clear(pool+i); while(m--) { getstring(); scanf("%d%d",&x,&y); if(s[0]=='C') connect(pool+x,pool+y); else if(s[0]=='D') del(pool+x,pool+y); else if(s[0]=='Q') ask(pool+x,pool+y)?puts("Yes"):puts("No"); } return 0;}
splay
#include<cstdio>const int INF=2000;inline int max(int a,int b){if(a>=b)return a;return b;}inline int min(int a,int b){if(a<=b)return a;return b;}inline void swap(int &a,int &b){a^=b;b^=a;a^=b;}struct stack{ int t; int a[500010]; inline void clear(){t=-1;} inline void push(int &n){a[++t]=n;} inline int top(){return a[t];} inline void pop(){t--;} inline bool empty(){return t<0;}}reuse;struct node{ int num,size,lmax,rmax,maxn,sum,id,rev; bool change; node *ch[2],*fa; inline void update() { size=ch[0]->size+ch[1]->size+1; sum=ch[0]->sum+ch[1]->sum; if(num!=-INF) sum+=num; lmax=max(ch[0]->lmax,max(ch[0]->sum+num,ch[0]->sum+ch[1]->lmax+num)); rmax=max(ch[1]->rmax,max(ch[1]->sum+num,ch[1]->sum+ch[0]->rmax+num)); maxn=max(ch[0]->maxn,ch[1]->maxn); maxn=max(maxn,max(ch[0]->rmax+num,ch[1]->lmax+num)); maxn=max(maxn,max(ch[0]->rmax+ch[1]->lmax+num,num)); } inline int getwh() { if(fa->ch[0]==this) return 0;return 1; } inline void pushchange(int n) { num=n; sum=size*n; maxn=lmax=rmax=max(num,sum); change=1; } inline void pushrev() { swap(lmax,rmax); node *tmp=ch[0];ch[0]=ch[1];ch[1]=tmp; rev^=1; } inline void setch(int wh,node *child); inline void pushdown();}pool[500010],*root,*null,*newroot;inline void node::setch(int wh,node *child){ ch[wh]=child; if(child!=null) child->fa=this; update();}inline void node::pushdown(){ if(rev) { if(ch[0]!=null) ch[0]->pushrev(); if(ch[1]!=null) ch[1]->pushrev(); rev=0; } if(change) { if(ch[0]!=null) ch[0]->pushchange(num); if(ch[1]!=null) ch[1]->pushchange(num); change=0; }}char s[10];int a[500010];int n,m,tot,x,y,z;inline void read(int &n){ n=0;char c=getchar();bool b=0; while(c<'0'||c>'9'){if(c=='-')b=1;c=getchar();} while(c>='0'&&c<='9') n=n*10+c-48,c=getchar(); if(b) n*=-1;}inline void getstring(){ int p=-1; char c=getchar(); while((c<'A'||c>'Z')&&c!='-') c=getchar(); while((c>='A'&&c<='Z')||c=='-') s[++p]=c,c=getchar();}inline node *getnew(int num){ node *now; if(!reuse.empty()) now=pool+reuse.top(),now->id=reuse.top(),reuse.pop(); else now=pool+ ++tot,now->id=tot; now->ch[0]=now->ch[1]=now->fa=null; now->num=now->sum=now->maxn=now->lmax=now->rmax=num; if(num==-1e9) now->sum=0; now->size=1; now->change=now->rev=0; return now;}inline void rotate(node *now){ node *fa=now->fa,*grand=now->fa->fa; int wh=now->getwh(); fa->setch(wh,now->ch[wh^1]); now->setch(wh^1,fa); now->fa=grand; if(grand!=null) { if(grand->ch[0]==fa) grand->ch[0]=now; else grand->ch[1]=now; }}inline void splay(node *now,node *tar){ for(;now->fa!=tar;rotate(now)) if(now->fa->fa!=tar) { if(now->getwh()==now->fa->getwh()) rotate(now->fa); else rotate(now); } if(tar==null) root=now;}node *build(int l,int r){ int mid=(l+r)>>1; node *now=getnew(a[mid]); if(l<mid) now->setch(0,build(l,mid-1)); if(r>mid) now->setch(1,build(mid+1,r)); return now;}inline node *kth(int rank){ node *now=root; int ranking=0; while(now!=null) { now->pushdown(); int tmp=ranking+now->ch[0]->size; if(tmp+1==rank) return now; if(tmp+1>rank) now=now->ch[0]; else ranking=tmp+1,now=now->ch[1]; }}inline void insert(node *newone,int pos){ splay(kth(pos),null); splay(kth(pos+1),root); root->ch[1]->setch(0,newone); root->update();}void dfs(node *now){ reuse.push(now->id); if(now->ch[0]!=null) dfs(now->ch[0]); if(now->ch[1]!=null) dfs(now->ch[1]);}inline void del(int pos,int n){ splay(kth(pos-1),null); splay(kth(pos+n),root); dfs(root->ch[1]->ch[0]); root->ch[1]->setch(0,null); root->update();}inline void changenum(int pos,int n,int num){ splay(kth(pos-1),null); splay(kth(pos+n),root); root->ch[1]->ch[0]->pushchange(num); root->ch[1]->update(); root->update();}inline void reverse(int pos,int n){ splay(kth(pos-1),null); splay(kth(pos+n),root); root->ch[1]->ch[0]->pushrev(); root->ch[1]->update(); root->update();}inline int sum(int pos,int n){ splay(kth(pos-1),null); splay(kth(pos+n),root); return root->ch[1]->ch[0]->sum;}int main(){ read(n),read(m); null=pool; null->ch[0]=null->ch[1]=null->fa=null; null->lmax=null->rmax=null->maxn=-INF; root=null; reuse.clear(); for(register int i=1;i<=n;i++) read(a[i]); a[0]=a[n+1]=-INF; root=build(0,n+1); while(m--) { getstring(); if(s[0]=='I') { read(x),read(y); for(register int i=1;i<=y;i++) read(a[i]); newroot=build(1,y); insert(newroot,x+1); } else if(s[0]=='D') read(x),read(y),del(x+1,y); else if(s[2]=='K') read(x),read(y),read(z),changenum(x+1,y,z); else if(s[0]=='R') read(x),read(y),reverse(x+1,y); else if(s[0]=='G') read(x),read(y),printf("%d\n",sum(x+1,y)); else printf("%d\n",root->maxn); } return 0;}
树链剖分
void dfs(int now,int fa,int depth){ deep[now]=depth; f[now]=fa; size[now]=1; int tmp=-INF; for(int i=head[now];i;i=a[i].next) if(a[i].to!=fa) { dfs(a[i].to,now,depth+1); size[now]+=size[a[i].to]; if(size[a[i].to]>tmp) tmp=size[a[i].to],son[now]=a[i].to; }}void dfs2(int now,int high){ top[now]=high; pos[now]=++tot; num[tot]=s[now]; if(son[now]) dfs2(son[now],high); for(int i=head[now];i;i=a[i].next) if(a[i].to!=f[now]&&a[i].to!=son[now]) dfs2(a[i].to,a[i].to);}void addpath(int x,int y,int z){ int L,R; if(top[x]==top[y]) { L=min(pos[x],pos[y]); R=max(pos[x],pos[y]); return Add(L,R,1,n,1,z); } if(deep[top[x]]<deep[top[y]]) swap(x,y); L=min(pos[x],pos[top[x]]); R=max(pos[x],pos[top[x]]); Add(L,R,1,n,1,z); return addpath(y,f[top[x]],z);}inline int LCA(int x,int y){ while(top[x]!=top[y]) if(deep[top[x]]>deep[top[y]]) x=f[top[x]]; else y=f[top[y]]; return deep[x]<deep[y]?x:y;}inline int Ask(int x){ if(root==x) return t[1].num; if(LCA(x,root)==x) { int ans=INF,from; for(int i=head[x];i;i=a[i].next) if(LCA(a[i].to,root)==a[i].to){from=a[i].to;break;} if(pos[from]>1) ans=min(ans,ask(1,pos[from]-1,1,n,1)); if(pos[from]+size[from]<=n) ans=min(ans,ask(pos[from]+size[from],n,1,n,1)); return ans; } return ask(pos[x],pos[x]+size[x]-1,1,n,1);}
计算几何
//凸包const double eps=1e-10;struct point{ double x,y; point(){} point(double xx,double yy):x(xx),y(yy){} inline point operator -(const point other)const { return point(x-other.x,y-other.y); } inline bool operator <(const point other)const { if(x==other.x) return y<other.y; return x<other.x; }}a[10005],s[10005];int n,top;double ans;inline int dcmp(double a,double b){ if(fabs(a-b)<eps) return 0; return a>b?1:-1;}inline double cross(point a,point b){ return a.x*b.y-a.y*b.x;}inline void solve(){ sort(a+1,a+n+1); for(int i=1;i<=n;i++) { while(top>1&&dcmp(cross(s[top]-s[top-1],a[i]-s[top-1]),0)<=0) top--; s[++top]=a[i]; } int num=top; for(int i=n-1;i;i--) { while(top>num&&dcmp(cross(s[top]-s[top-1],a[i]-s[top-1]),0)<=0) top--; s[++top]=a[i]; }}//半平面交#include<cmath>#include<cstdio>#include<algorithm>using namespace std;const double INF=1e100;const double eps=1e-10;const int N=305;struct point{ double x,y; point(){} point(double xx,double yy):x(xx),y(yy){} inline point operator +(const point other)const { return point(x+other.x,y+other.y); } inline point operator -(const point other)const { return point(x-other.x,y-other.y); } inline point operator *(const double other)const { return point(x*other,y*other); }};inline int dcmp(double a,double b){ if(fabs(a-b)<eps) return 0; return a>b?1:-1;}inline double cross(point a,point b){ return a.x*b.y-b.x*a.y;}inline double supercross(point a,point b,point c){ return cross(point(b.x-a.x,b.y-a.y),point(c.x-b.x,c.y-b.y));}struct line{ point s,v; line(){} line(point ss,point vv):s(ss),v(vv){} inline bool operator <(const line other)const { double rate1=atan2(v.y,v.x),rate2=atan2(other.v.y,other.v.x); if(!dcmp(rate1,rate2)) return dcmp(supercross(s,s+v,other.s),0)==-1; else return rate1<rate2; }};inline point inter(line a,line b){ point u=b.s-a.s; double rate=cross(u,b.v)/cross(a.v,b.v); return a.s+(a.v*rate);}inline bool onleft(line a,point p){ return dcmp(supercross(a.s,a.s+a.v,p),0)>0;}inline double high(point a,point b,double p){ return inter(line(a,b-a),line(point(p,0),point(0,1))).y;}struct halfinter{ line a[N],q[N]; int n,h,t; point tmp[N]; inline void solve() { sort(a+1,a+n+1); q[h=t=1]=a[1]; for(int i=2;i<=n;i++) { if(!cross(a[i].v,a[i-1].v)) continue; while(h<t&&!onleft(a[i],inter(q[t-1],q[t]))) t--; while(h<t&&!onleft(a[i],inter(q[h],q[h+1]))) h++; q[++t]=a[i]; } while(h+1<t&&!onleft(q[h],inter(q[t],q[t-1]))) t--; while(h+1<t&&!onleft(q[t],inter(q[h],q[h+1]))) h++; for(int i=h;i<t;i++) tmp[i]=inter(q[i],q[i+1]); }}half;int x[N],y[N];int n;double ans=INF;int main(){ scanf("%d",&n); for(int i=1;i<=n;i++) scanf("%d",&x[i]); for(int i=1;i<=n;i++) scanf("%d",&y[i]); for(int i=1;i<n;i++) half.a[i]=line(point(x[i],y[i]),point(x[i+1]-x[i],y[i+1]-y[i])); half.n=n+1; half.a[n]=line(point(x[1],0),point(0,-1)); half.a[n+1]=line(point(x[n],0),point(0,1)); half.solve(); for(int i=half.h,j=1;i<=half.t;i++) { while(dcmp(x[j],half.tmp[i].x)>0||dcmp(half.tmp[i].x,x[j+1])>0) j++; ans=min(ans,half.tmp[i].y-high(point(x[j],y[j]),point(x[j+1],y[j+1]),half.tmp[i].x)); } for(int i=1,j=half.h;i<=n;i++) { while(dcmp(half.tmp[j].x,x[i])>0||dcmp(x[i],half.tmp[j+1].x)>0) j++; ans=min(ans,high(half.tmp[j],half.tmp[j+1],x[i])-y[i]); } printf("%.3lf",ans); return 0;}
0 0
- 板子
- 板子
- 测试板子
- 板子总结
- 入手板子
- 新板子
- Ivus 板子
- dinic 板子
- manacher板子
- 左偏树 板子
- NTT板子
- RMQ板子
- spfa板子
- kmp板子
- manacher板子
- LCA板子
- OI板子
- KD_tree 板子
- Python:如何使用jupyter绘制caffe训练过程中的loss和accuracy曲线?n
- PL/SQL Developer连接本地Oracle 11g 64位数据库
- 01普通背包和01满背包问题
- C++中public、protected及private用法
- python 数据分析学习笔记 (第三章)
- 板子
- 测试理论
- module_platform_driver宏解析
- CF
- windows系统所有管理员权限操作无法运行,提示"系统找不到指定路径"的解决方法.
- c++基础之STL
- Kadane算法
- Windows,查看同网段所有能Ping通的IP地址
- Anton and Permutation CF